4장 반복문
1. 리스트와 반복문
1) while 문 * 3초 동안 반복하는 프로그램
# 반복문 while
# 시간을 기반으로 반복
# 유닉스 타임 = 1970년 1월 1일 0시 0분 0초를 기준으로 몇초가 지났는지 알려줌
# 3초 동안 반복하는 프로그램
import time # time 모듈 불러오기
no = 0 # no 변수 초기화
target = time.time() + 3 # 3초 후의 시간을 target 변수에 저장
while time.time() < target : # 현재 시간이 target 시간보다 작을 때까지 반복
no +=1 # no 변수에 1씩 더해줌
print(no) # no 값 출력
* 실행 종료 선택 프로그램 break, continue
# 키워드 break
i = 0 # 초기값 설정
while True: # 무한루프
print(i) # i 출력
i += 1 # i 증가
yn = input("종료할까요?(원하시면 y나 Y를 입력하세요)> ") # 사용자 입력 받기
if yn in ["y", "Y"]: # yn 값이 "y"나 "Y"와 같으면
print("반복 종료") # "반복 종료" 출력
break # 반복문 종료
# 키워드 continue
no = [100, 10, 110, 20]
for i in no:
if i <= 100: # i가 100 이하인 경우 아래 코드를 실행하지 않고 다음 반복으로 넘어감
continue
else:
print(i) # i가 100보다 큰 경우 i를 출력함
2) 247p~249문제 !!! 중요
* 1번 (range문제)
# 1-2번 문제 247p
a=list(range(7,0,-1))
print(a)
* 2번 문제 (for문을 통한 dict 생성)
# 2번 문제 248p
# 딕셔너리 생성을 위한 키, 값 리스트 생성
key_list = ["name", "hp", "mp", "level"]
value_list = ["기사", 200, 30, 5]
# 빈 딕셔너리 생성
character = {}
# key_list와 value_list를 이용하여 딕셔너리 생성
for i in range(len(key_list)):
character[key_list[i]] = value_list[i]
# 생성된 딕셔너리 출력
print(character)
* 3번 문제 (while문, break를 통한 최종 값 구하기 // 10000이 넘는 경우를 구하기)
# 3번 문제 248p # break를 넣을 경우
# 이 코드는 먼저, 10000이라는 값을 limit에 할당합니다.
# 그리고 i와 sum_value 변수를 1과 0으로 초기화합니다.
# while 루프에서는 무한 루프를 돌면서 sum_value에 i 값을 더해주고,
# 만약 sum_value가 limit보다 크거나 같아지면 break 문을 이용해서 while 루프를 빠져나옵니다.
# 마지막으로 print 함수를 이용해 i, limit, sum_value를 출력합니다.
# 이 코드는 1부터 차례대로 더해가면서 limit보다 커지는 순간을 찾아내는 방법을 이용하여 i와 sum_value를 출력합니다.
# limit 변수에 최대 더해질 수 있는 값(최댓값)을 할당합니다.
limit = 10000
# i 변수에 첫번째 더할 값인 1을 할당하고, sum_value 변수에 초기값 0을 할당합니다.
i = 1
sum_value = 0
# while 루프를 돌면서 sum_value에 i 값을 더해주고, sum_value가 limit 이상이 되면 루프를 중단합니다.
while True:
sum_value += i
if sum_value >= limit:
break
# i 값에 1을 더해줍니다.
i += 1
# 결과를 출력합니다.
print("{}를 더할 때 {}을 넘으며 그때의 값은 {}입니다.".format(i, limit, sum_value))
# 3번 문제 248p # break를 넣지 않은 경우 (print에서 조절)
limit = 10000 # 더한 결과가 이 값 이상이 되면 루프를 멈춥니다.
i = 1 # 더할 정수를 1부터 시작합니다.
sum_value = 0 # 더한 결과를 담을 변수입니다.
while sum_value <= limit:
sum_value += i
i += 1
print("{}를 더할 때 {}을 넘으며 그때의 값은 {}입니다.".format(i-1, limit, sum_value))
*4번 문제 249p (for문과 if문을 활용하여 최대가 되는 경우를 구하기 // 범위 range 활용)
# 4번 문제 249p
max_value = 0 # 최대값을 저장할 변수
a = 0 # 최대값일 때의 i 값
b = 0 # 최대값일 때의 j 값
for i in range(1, 51): # i는 1부터 50까지 반복
j = 100 - i # i와 j의 합이 100이 되도록 j를 계산
value = i * j # i와 j의 곱을 계산
if value > max_value: # 곱이 현재까지의 최대값보다 크면 최대값과 최대값일 때의 i, j 값을 갱신
max_value = value
a = i
b = j
print("최대가 되는 경우: {} * {} = {}".format(a, b, max_value)) # 최대값일 때의 i, j 값과 곱을 출력
* 위의 계산 식을 직접 보면서 배우는 팁
a = []; b = []; c = []
# 1부터 5까지 반복하면서 j값 구하고 a, b, c 리스트에 append
for i in range(1, 5+1):
j = 10 - i
current = i * j
a.append(i)
b.append(j)
c.append(current)
# a, b, c 리스트 출력
print(a)
print(b)
print(c)
3) 문자열,리스트,딕셔너리와 관련된 함수
* min,max,sum
# 함수
# 리스트에 사용할 수 있는 함수
a = [1,2,3,4,5]
print(min(a))
print(max(a))
print(sum(a))
* reversed
# 요소 순서 거꾸로 바꾸기
a = [1,2,3,4,5]
b = reversed(a)
print(a)
print(b)
print(list(b))
# 변수로 쓰지 말고 함수 적용을 바로 써야 함
a = reversed([1,2,3,4,5])
for i in a:
print(i)
for i in a:
print(i)
# 변수로 쓰지 말고 함수 적용을 바로 써야 함
for i in reversed([1,2,3,4,5]):
print(i)
for i in reversed([1,2,3,4,5]):
print(i)
* index & 값 출력
# 인덱스 & 값 출력
# 1) 리스트 반복
example_list = ["A", "B", "C"]
i = 0
# 리스트 example_list를 반복하면서 인덱스 i와 해당 값을 출력한다.
for j in example_list:
print(i, j)
# 인덱스 i를 1씩 증가시킨다. # 다음 인덱스로 이동하기 위해 i에 1 더하기
i += 1
# 2) 범위 & 리스트 반복
example_list = ["A","B","C"]
for i in range(len(example_list)): # example_list 길이 만큼 반복
print(i,example_list[i]) # i와 example_list[i] 출력
# 3) enumerate() => 튜플 형태로 반환
# enumerate()를 사용하여 리스트를 인덱스와 함께 출력하는 코드
example_list = ["A","B","C"]
print(example_list) # 리스트 전체 출력
print(enumerate(example_list)) # enumerate() 함수 사용시 객체 출력
for i,j in enumerate(example_list): # enumerate() 함수로 i는 인덱스, j는 값으로 각각 반복문에서 사용
print(i,j)
* dict 튜플 이해하기
# 딕셔너리의 키와 값을 출력하는 코드
example_dictionary = {
"키1": "값1",
"키2": "값2",
"키3": "값3"
}
for i, j in example_dictionary.items(): # items() 메소드로 키와 값을 각각 변수 i와 j에 할당하고 반복
print(i, j) # 각각의 i와 j를 출력
# 리스트 내포
# 1부터 5까지의 숫자 리스트를 만들고, 그 리스트를 이용해 각 원소의 제곱을 구하는 코드
a = [] # 빈 리스트 a 생성
b = [] # 빈 리스트 b 생성
for i in range(1,5+1): # 1부터 5까지 반복
a.append(i) # 리스트 a에 i를 추가
b.append(i **2) # 리스트 b에 i의 제곱을 추가
print(a) # 리스트 a 출력
print(b) # 리스트 b 출력
c=[i**2 for i in range(1,5+1)]
print(c) # 리스트 내포를 사용하여 1부터 5까지 제곱한 값을 c 리스트에 저장하고 출력
# 리스트 내포에서 조건문 추가
# "토마토"를 제외한 과일만 리스트 b에 추가하는 코드
a = ["사과", "체리", "딸기", "토마토", "복숭아"]
b = [fruit for fruit in a if fruit != "토마토"]
print(b) # 리스트 b 출력
* 들여쓰기 문제
# 여러 줄의 문자열을 출력할 때 들여쓰기가 되는 문제 해결
no = int(input("정수 입력>"))
if no % 2 == 0: # 짝수
# 여러 줄의 문자열을 출력할 때는 맨 앞에 "\"를 붙여서 해결할 수 있다.
print("""\
입력한 숫자는 {}입니다.
{}는 짝수입니다.""".format(no,no))
else: # 홀수
# 여러 줄의 문자열을 출력할 때는 맨 앞에 "\"를 붙여서 해결할 수 있다.
print("""\
입력한 숫자는 {}입니다.
{}는 홀수입니다.""".format(no,no))
# 여러 줄의 문자열을 출력할 때 코딩의 들여쓰기 통일성이 저해되는 문제를 해결하기 위해
# 문자열 앞에 \를 붙여서 들여쓰기가 되는 문제를 해결합니다.
no = int(input("정수 입력>"))
if no % 2 == 0: # 짝수
print("""\
입력한 숫자는 {}입니다.
{}는 짝수입니다.""".format(no, no))
else: # 홀수
print("""\
입력한 숫자는 {}입니다.
{}는 홀수입니다.""".format(no, no))
# 여러 줄의 문자열을 출력할 때 코딩의 들여쓰기 통일성이 저해 되는 문제
no = int(input("정수 입력>"))
if no % 2 == 0: # 짝수
print("""입력한 숫자는 {}입니다.\n{}는 짝수입니다.""".format(no,no))
else: # 홀수
print("""입력한 숫자는 {}입니다.\n{}는 홀수입니다.""".format(no,no))
* join 사용
no = int(input("정수 입력>"))
if no % 2 == 0: # 짝수
print("\n".join(["입력한 숫자는 {}입니다.\n{}는 짝수입니다."]).format(no,no))
else: # 홀수
print("\n".join(["입력한 숫자는 {}입니다.\n{}는 홀수입니다."]).format(no,no))
* 이터레이터
# 이터레이터
a = [1,2,3]
b = reversed(a)
print(b)
# print(list(b))
print(next(b))
print(next(b))
print(next(b))
4) 확인 문제 !!! 266p
* 1번 문제 enumerate()함수와 items()함수의 올바른 표기법
enumerate() : enumerate(리스트)
items() : 딕셔너리.itmes()
* 2번 문제
# 266p~267p
# 1번 문제는 2,3번
# 2번 문제 (1~100 사이에 있는 숫자 중 2진수로 변환했을 때
# 0이 하나만 포함된 숫자를 찾고, 그 숫자들의 합을 구하는 코드를 만들어 보세요.)
output = [] # 2진수에서 0이 하나만 있는 숫자들을 저장할 리스트 생성
for i in range(1,101): # 1부터 100까지의 수에 대해 반복
binary = bin(i)[2:] # i를 2진수로 변환하여 문자열 형태로 저장 (첫 두 글자 "0b"는 제외)
if binary.count("0") == 1: # 2진수에서 "0"의 개수가 1인 경우
output.append(i) # output 리스트에 i 추가
for i in output: # output 리스트에 저장된 숫자들에 대해 반복
print("{} : {}".format(i, "{:b}".format(i))) # 숫자와 해당 숫자의 2진수 표기 출력
print("합계:",sum(output)) # output 리스트에 저장된 숫자들의 합 출력
# 2번 문제 교수님 풀이
# 리스트 내포를 사용하여 코드를 간결하게 작성
output = [i
for i in range(101) # 1부터 100까지의 숫자를 대상으로 함
if "{:b}".format(i).count("0") == 1] # 2진수 변환 후 0의 개수가 1인 숫자를 선택
for i in output:
print("{} : {}".format(i, "{:b}".format(i))) # 선택된 숫자와 2진수 출력
print("합계:", sum(output)) # 선택된 숫자들의 합을 계산하여 출력
# 2번 문제 교수님 풀이 수정 부분 // if i !=0 추가
output = [i # 1부터 100까지 반복하며
for i in range(101)
if "{:b}".format(i).count("0") == 1] # i를 이진수로 변환하여 0의 개수가 1인 경우에만 리스트에 추가
for i in output: # output 리스트의 요소들에 대해서 반복
if i != 0: # i가 0일 경우 이진수 변환 시 '0'이 반환되기 때문에 제외
print("{} : {}".format(i, "{:b}".format(i))) # i와 i를 이진수로 변환한 결과 출력
print("합계:", sum(output)) # output 리스트의 합 출력
5) 도전문제!!!! 268p
* 1번 문제 - 숫자의 종류를 구하기
** 교수님 풀이
# 1번 문제 // 교수님 풀이
a = [1, 2, 3, 4, 1, 2, 3, 1, 4, 1, 2, 3] # 주어진 리스트 a 생성
b = {} # 빈 딕셔너리 b 생성
for i in a: # 리스트 a의 모든 요소에 대해서 반복문 실행
if i in b: # 만약 딕셔너리 b에 현재 요소 i가 이미 있다면
b[i] += 1 # 해당 요소의 개수를 1 증가시킴
else: # 만약 딕셔너리 b에 현재 요소 i가 없다면
b[i] = 1 # 해당 요소의 개수를 1로 설정함
print("{}에서".format(a))
print("사용된 숫자의 종류는 {}개입니다.".format(len(b))) # b의 길이를 이용하여 사용된 숫자의 종류의 개수를 출력함
print("참고: {}".format(b)) # 딕셔너리 b를 출력하여 각 숫자가 몇 번 사용되었는지 나타냄
** 나
# 1번 문제 (숫자의 종류) 268p
# 주어진 리스트 a에서 각 숫자가 몇 번 사용되었는지 딕셔너리로 저장
a = [1,2,3,4,1,2,3,1,4,1,2,3]
b = {i: a.count(i) for i in set(a)}
# 결과 출력
print("{}에서\n사용된 숫자의 종류는 {}개입니다.\n참고: {}".format(a, len(set(a)), b))
* 2번 문제 - 염기의 개수
** 교수님
# 2번 문제 교수님 // 대문자 입력 안 됨, 그 이외에 값을 넣으면 그냥 오류 메시지 발생
a = input("염기 서열을 입력해주세요: ")
b = {"a":0, "t":0, "g":0, "c":0} # 딕셔너리 b를 초기화
for i in a: # 문자열 a를 하나씩 읽어들임
b[i] += 1 # 읽어들인 문자에 해당하는 키 값을 가진 b의 딕셔너리 값을 1 증가시킴
for j in b: # 딕셔너리 b에서 키 값을 하나씩 읽어들임
print("{}의 개수 : {}".format(j,b[j])) # 키와 그에 해당하는 값(문자의 개수)을 출력
# 2번 문제 교수님 심화 // 대문자 입력 안 됨, 그 이외에 값을 넣으면 그냥 오류 메시지 발생
# a,t,g,c 만 입력하게 하려면 그냥 인풋 설명에 입력하는게 좋음.
# 딕셔너리 생성 없이 함수 이용해서 해결
from collections import Counter # 자료의 개수를 셀 때 유용하게 사용됩니다.
# 사용자로부터 염기 서열을 입력받습니다.
a = input("염기 서열을 입력해주세요: ")
# Counter 클래스를 사용하여 각 문자의 개수를 세어서 딕셔너리 형태로 저장합니다.
b = Counter(a)
# 딕셔너리 b를 순회하며 각 문자의 개수를 출력합니다.
for j in b:
print("{}의 개수 : {}".format(j, b[j]))
** 나
# 2번 문제 (염기의 개수) 268p // ATGC 이외의 값을 추가하면 출력 안되게끔
sequence = input("염기 서열을 입력하세요\n예)ATGCatgc \n") # 사용자로부터 염기 서열을 입력받음
nucleotides = {'a':0, 't':0, 'g':0, 'c':0} # 염기 서열에서 'a', 't', 'g', 'c'가 나올 때마다 개수를 저장할 딕셔너리 초기화
while True: # 무한 루프
valid = True # 입력된 염기 서열이 올바른지 여부를 저장하는 변수
for n in sequence: # 입력된 염기 서열에서 각 염기를 반복
if n.lower() in nucleotides: # 염기가 'a', 't', 'g', 'c' 중 하나인지 확인
nucleotides[n.lower()] += 1 # 염기의 개수를 1 증가
else:
valid = False # 올바르지 않은 염기 서열임을 표시
print("atgc 이외의 문자가 포함되어 있습니다.")
sequence = input("다시 입력해주세요.\n") # 올바른 염기 서열을 다시 입력받음
nucleotides = {'a':0, 't':0, 'g':0, 'c':0} # 염기 개수를 다시 초기화
break # 입력된 염기 서열에서 'atgc' 이외의 문자가 발견된 경우 루프를 종료하고 처음부터 다시 시작
if valid: # 입력된 염기 서열이 올바르면
break # 무한 루프를 종료하고 다음 코드를 실행
# 'a', 't', 'g', 'c'의 개수 출력
print("a의 개수 : {}".format(nucleotides['a']))
print("t의 개수 : {}".format(nucleotides['t']))
print("g의 개수 : {}".format(nucleotides['g']))
print("c의 개수 : {}".format(nucleotides['c']))
* 3번 문제 - 코돈의 개수
** 교수님 풀이
# 3번 문제 (코돈의 개수) // 교수님 풀이
a = input("염기 서열을 입력해주세요\n(염기서열 atgc만 입력해주세요):\n") # DNA 서열을 입력받습니다.
b = {} # 빈 딕셔너리를 생성합니다.
for i in range(0, len(a), 3): # range 함수를 사용하여 a의 인덱스를 0부터 시작하며 3씩 증가시킵니다.
c = a[i:i+3] # 인덱스 i부터 i+3까지의 염기를 추출하여 c에 저장합니다.
if len(c) == 3: # 추출한 코돈이 3개의 염기로 이루어져 있다면, 코돈의 개수를 세는 작업을 진행합니다.
if c in b: # c가 b에 있는 키 값 중 하나인 경우, 해당 키의 값에 1을 더합니다.
b[c] += 1
else: # c가 b에 없는 키인 경우, 새로운 키로 추가하고 값을 1로 설정합니다.
b[c] = 1
print(b) # b 딕셔너리를 출력합니다.
** 나
# 3번 문제 (코돈의 개수) 269p // 대소문자 구분없이 입력받고 ATGC 이외의 값을 추가하면 출력 안되게끔
codons = {} # 빈 딕셔너리 생성
while True:
sequence = input("염기 서열을 입력하세요\n(염기서열은 A,T,G,C입니다) \n")
if set(sequence.upper()) - set('ATGC'): # 입력값이 ATGC 이외의 문자를 포함하면 다시 입력 받음
print("ATGC 이외의 문자가 포함되어 있습니다. 다시 입력해주세요.")
else:
break
sequence = sequence.upper() # 입력값을 모두 대문자로 변환
i = 0
while i < len(sequence)-2: # 염기서열의 마지막 세 자리를 제외한 모든 코돈을 추출함
codon = sequence[i:i+3]
if codon in codons: # 추출한 코돈이 이미 딕셔너리에 있다면 값에 1을 더함
codons[codon] += 1
else: # 딕셔너리에 코돈이 없다면 값을 1로 설정함
codons[codon] = 1
i += 3
print(codons) # 코돈과 해당 코돈의 개수를 출력함
* 4번 문제 - 2차원 리스트 평탄화 270p
** 교수님
# 도전문제4
a = [1,2,[3,4],5,[6,7],[8,9]]
b = []
for i in a:
if type(i) == list:
for j in i:
b.append(j)
else:
b.append(i)
print("{}를 평탄화하면 \n{}입니다.".format(a,b))
* 나
# 4번 문제 2차원 리스트 평탄화 270P
def flatten(lst):
flattened = [] # 평탄화된 1차원 리스트를 저장할 리스트
for elem in lst: # 리스트의 원소들을 하나씩 순회
if type(elem) == list: # 원소가 리스트일 경우
flattened.extend(flatten(elem)) # 재귀적으로 평탄화하여 flattened 리스트에 추가
else: # 원소가 리스트가 아닐 경우
flattened.append(elem) # flattened 리스트에 원소 추가
return flattened # 평탄화된 1차원 리스트 반환
a = [1,2,[3,4],5,[6,7],[8,9]]
b = flatten(a)
print("{}를 평탄화하면\n{}입니다".format(a,b))
* 정리
- 튜플은 값을 고정시키는 것이다.
* 핵심
주석 이해하면서 연습문제 꼭 풀어보기
* 링크 (직접 글 쓴 당사자만 확인 가능 // 계정 이동해서 확인하기)
'배운 책들 정리 > 혼자 공부하는 파이썬' 카테고리의 다른 글
혼자 공부하는 파이썬 5,6 - 함수 고급, 예외 처리 (1) | 2023.04.18 |
---|---|
혼자 공부하는 파이썬 5 - 함수 만들기, 함수의 활용 (1) | 2023.04.17 |
혼자 공부하는 파이썬 4 - 반복문(조건문 응용(if), dict, list, 이중for문, range, while문) (0) | 2023.04.13 |
혼자 공부하는 파이썬 2,3,4 - 숫자와 문자열의 다양한 기능, 조건문, 반복문 (0) | 2023.04.11 |
혼자 공부하는 파이썬 2 - 자료형(변수) (0) | 2023.03.28 |