앞 장에서 우리는 무한 루프 구조를 살짝 경험해보았다.
프로그램에서 "반복" 이라는 것은 큰 의미를 가진다.
프로그램을 작성하는 것은 결국 우리가 직접 하기 어려운 일들을 컴퓨터에게 맡기는 것인데,
어떤 일을 반복해야 하는 횟수가 클수록 컴퓨터에게 맡겼을 때의 효율은 올라간다.
"반복" 하기 위해서는 반복문을 사용하는데, 반복 구조를 사용하면 프로그램이 간결해지게 된다.
예를 들어 동일한 작업을 반복하기 위해 똑같은 문장을 복사하여 붙여넣기 하는 것보다
반복 구조를 사용하는 편이 프로그램을 간결하게 만든다.
또 프로그래밍에 필요한 시간도 단축할 수 있다.
반복문을 간단하게 맛보자.
for i in range(100) :
print("파이썬을 열심히 공부하자!")
뒤에서 배우겠지만 해당 코드는 문자열을 100번 반복해서 출력하는 코드이다.
해당 코드를 실행해보면
문자열이 훨씬 많이 출력되었지만 생략하겠다.
이런 식으로 반복문을 사용하면 반복해서 해야 할 작업을 간단히 작성할 수 있다.
반복문을 사용하지 않았다면 print() 문을 100번 입력해야 했을 것이다.
파이썬에는 2가지 종류의 반복이 있다.
- 횟수 제어 반복 (for 문) : 보통 횟수를 정해 놓고 반복
- 조건 제어 반복 (while 문) : 특정한 조건이 만족되면 계속 반복
횟수 제어 반복은 반복을 시작하기 전에 반복의 횟수를 미리 아는 경우에 사용한다.
예를 들어서 "환영합니다" 문장을 5번 반복하여 출력한다면 for 문을 사용하면 자연스럽다.
파이썬은 항목들을 모아 놓은 시퀀스라는 객체가 있는데,
여기에서 항목을 하나씩 가져와서 반복할 때도 for 문이 적합하다.
위의 코드를 보면 range() 함수가 나오는데 range(5) 라고 하면, 0, 1, 2, 3, 4 의 숫자 시퀀스를 자동 생성한다.
따라서 for i in range(5) 와 같이 반복문을 구성하면,
0에서 4까지의 숫자를 반환하는 작업을 끝날 때까지 반복 실행된다.
반면 while 문의 경우 (조건 제어 반복), while i < 5 와 같이 조건을 구성하고
한 번 실행할 때마다 i 의 값을 1씩 증가시켜서 반복시키면 동일하게 5회 반복이 실행된다.
먼저 for loop 를 살펴보자. (loop 란 프로그램이 반복하는 것을 의미한다.)
for loop 는 반복할 횟수를 정해 두고, 이 횟수가 만족될 때까지 같은 동작을 반복하도록 한 것이다.
for loop 를 사용할 때는 다음과 같이 리스트를 이용하여 사용하는 방식을 연습해보자.
여기서 [...] 은 리스트인데, 이것은 나중에 더 알아보도록 하고, 여기서는 여러 개의 값을 담을 수 있는
바구니 정도로만 이해하면 되겠다.
for i in [1, 2, 3, 4, 5] :
print("Hello")
위 코드는 리스트에서 값을 하나씩 꺼내와서 변수 i 에 저장하고 아래 블록을 실행한다.
그러다가 더 이상 꺼낼 값이 없으면 반복문을 종료하는 것이다.
반복문도 앞 장에서의 if 문과 마찬가지로 : 이후 실행문은 들여쓰기를 해야 하고,
동일 칸 만큼 들여쓰기한 부분은 한 블록이 되어 반복문이 실행되게 된다.
위 예제에서는 변수 i 의 값은 사용하지 않고 반복 횟수로만 사용했는데,
반복문을 공부할 때 빼놓을 수 없는 구구단 예제로 변수 i의 값도 한 번 사용해보자.
구구단의 9단을 출력하는 예제를 만들어보자.
1부터 9까지의 리스트를 만들고 하나씩 꺼내 변수 i 에 담는다.
그리고 print() 를 통해서 9 x 1 부터 9 x 9 까지 출력하면 될 것이다.
아래 코드는 그 해답이다.
for i in range(1, 10) :
print("9 x", i, "=", 9 * i)
출력 결과는 다음과 같다.
여기서 range() 함수가 등장하는데, 위에서 얘기한대로 [1, 2, 3, 4, 5, 6, 7, 8, 9] 의 리스트를
range() 자리에 넣어도 동일하게 동작한다.
range() 함수는 for loop 에서 굉장히 빈번하게 사용되는데,
구구단과 같이 반복횟수가 몇 번 되지 않는 경우에는 for i in [1, 2, 3, 4, 5, 6, 7, 8, 9] 와 같이 작성해도 무방하지만,
반복횟수가 천 번, 만 번이라면 이 방법이 불가능하다.
이 때 range() 함수로 반복 횟수를 전달하면 range() 함수가 자동으로 정수들을 생성해준다.
예를 들어 range(5) 함수는 5개의 정수를 생성한다. 0, 1, 2, 3, 4 가 바로 그것이다.
그리고 for loop 는 이 시퀀스의 개수만큼 반복수행한다.
range() 함수는 여러 개의 인자를 이용하여 좀 더 다양한 정수 시퀀스를 생성할 수 있으며,
일반적인 형식은 다음과 같다. range(start, stop, step) 이라고 호출하면, start 에서 시작하여 (stop-1) 까지
step 의 간격으로 정수들이 생성된다.
여기서 start 와 step 이 생략될 수 있는데, 이 경우 start 는 0으로 간주되고 step 은 1로 간주된다.
하지만 stop 값은 반드시 지정해야만 루프가 수행된다.
이번에는 while 문을 한 번 살펴보자.
횟수를 알 수 없는 경우에만 while loop 를 사용할 수 있는 것은 아니다.
횟수를 알고 있는 경우에도 while loop 를 사용할 수 있다.
예를 들어 사용자로부터 특정한 수를 입력받아 구구단의 특정 단을 while 반복문을 이용하여 출력하여 보자.
dan = int(input('원하는 단은 : '))
i = 1
while i <= 9 :
print("%s*%s=%s" % (dan, i, dan*i))
i += 1
여기서 문자열과 변수를 함께 출력하기 위해서 연결하는 방식을 사용했다.
"" 안의 %s 는 뒤의 변수를 문자열 형태로 불러 mapping 한다고 생각하면 된다.
예를 들어 print("%s" % (name)) 이라는 코드에서
name 에는 이름에 해당하는 문자열이 들어있다고 가정하면
name 변수에 들어있는 문자열이 print() 를 통해서 출력된다.
이 때 "%s" 와 (name) 사이의 %가 그 연결고리 역할을 수행한다.
위의 코드에서 %s 가 세 번 나왔으니, 뒤의 세 개의 데이터가 각각 mapping 되어 출력된다.
이처럼 while 문을 이용해서 구구단을 출력할 수 있다.
이번에는 해당 조건이 False 가 될 때까지 미리 횟수를 정해놓지 않고 반복문을 수행하는
while loop 를 실습해보자.
사용자가 입력한 숫자들을 더하는 프로그램을 작성해보자.
사용자가 'yes' 라고 대답하면 계속 숫자를 입력받아서 더하고,
'no' 라고 입력하는 순간 while loop 를 종료하고 다 더해진 숫자를 출력하고 끝난다.
해답 코드는 다음과 같다.
total = 0
answer = 'yes'
while answer == 'yes' :
number = int(input('숫자를 입력하시오 : '))
total += number
answer = input('계속? (yes/no) : ')
print('합계는 : ', total)
위 코드를 실행하면 다음과 같은 결과가 출력된다.
for 문은 while 문으로 고쳐 쓸 수 있고, 마찬가지로 while 문 역시 for 문으로 고쳐 쓸 수 있다.
하지만 for 문의 형식은 횟수가 정해져 있는 반복에 적합하고,
while 은 횟수를 정해 놓지 않고 변화하는 조건을 체크하며 반복하는 일에 적합하다.
조건 제어 루프에서 가끔은 프로그램이 무한히 반복하는 일이 발생할 수 있다.
이전에서 살펴보았던 "무한 루프" 가 그것이다.
하지만 의도적으로 무한 루프를 만들고 특정 조건에서만 반복문이 종료되는 상황을
만들어야 할 때도 있다.
그럴 때는 break 문을 이용해서 반복문을 빠져나올 수 있다.
예제를 한 번 살펴보자.
while True :
light = input('신호등 색상을 입력하시오 : ')
if light == 'green' :
break
print('전진!')
위 코드에서 화면에 '신호등 색상을 입력하시오' 를 출력하고 사용자의 입력을 기다린다.
while True : 로 되어 있으므로 무한 루프이다. 사용자가 'green' 을 입력하면 break 문장을 실행하면서
무한 루프를 빠져나간다. 사용자가 입력한 색상이 'green' 이 아니면 이 루프는 무한히 반복한다.
break 문으로 가장 가까운 반복문 블럭을 즉시 빠져나올 수 있다면,
loop 안에서 특정 문장을 건너뛰고 다시 반복문을 수행시킬 수는 없을까?
가능하다. 바로 continue 를 이용하면 된다.
이 키워드는 loop 를 빠져나오지 않고 continue 아래의 문장을 건너뛰는 역할을 한다.
하지만 break 와 continue 문이 너무 많이 사용되는 경우 제어의 흐름에 일관성이 없어
프로그램을 이해하는 것이 어려워진다.
따라서 break 와 continue 는 필요한 경우에만 제한적으로 사용하는 것이 좋다.
여기까지 반복문에 대한 얘기는 끝이다.
추가적으로, 출력을 가지런히 하는 방법에 대해 덧붙이고자 한다.
print() 를 이용해 출력을 할 때, 다양한 방법으로 출력을 할 수 있다.
그럴 때 사용하는 메소드가 바로 format() 메소드인데 {} (플레이스홀더) 를 이용하여 원하는 문자나 숫자를
적절한 포맷으로 출력할 수 있다.
여기서 {}는 format() 메소드의 인자로 들어오는 값이 출력되는 위치를 지정하는 역할을 한다.
print('{} Python!'.format('Hello'))
# Hello Python
print('I like {} and {}'.format('Python', 'Java'))
# I like Python and Java
주석처리된 부분이 해당 코드 실행 시 출력되는 결과이다.
{} 안에 0, 1, 2 와 같은 인덱스를 활용하여 인자값을 지정할 수도 있다.
또한 출력을 할 시 전체 필드의 폭을 지정할 수도 있다.
for i in range(2, 11, 2) :
print('{0:3d} {1:4d} {2:5d}'.format(i, i*i, i*i*i))
위 코드를 살펴보면 {} 안의 0, 1, 2는 각각의 인덱스로,
format() 세 개의 인자 각각을 연결시킨다.
d 는 정수를 출력한다는 의미이고, d 앞의 3, 4, 5의 숫자는 각각
몇 칸을 필드의 폭으로 할 것인지를 의미한다.
실행 결과는 다음과 같다.
출력이 가지런하게 포매팅되어 나오는 것을 확인할 수는 있다.
이제 반복문과 포매팅에 대한 얘기까지 마무리했으니,
다음엔 함수에 대한 얘기를 해보자.
이번 장에서 반복문에 대한 공부를 하며 이제 문법적인 부분은 많이 익숙해진 것 같다.
하지만 익숙해졌다고 해도 계속해서 조건문과 반복문에서 들여쓰기를 잘못 한다던지 등등의
실수를 한다는 것을 느꼈다. 뭐든지 작은 코딩부터 하는 습관을 들이고 여러 모듈을 사용해보면서
경험을 쌓아나가면 프로그래밍의 실력이 쌓일 것이라 생각된다.
출처 : 따라하며 배우는 파이썬과 데이터 과학 - 천인국, 박동규, 강영민