23.02.20 Day16

오윤범·2023년 2월 20일
0

알고리즘

백준(수업)

  • 백준 1253번 좋다

# 백준 1253 좋다
import sys
input=sys.stdin.readline
N=int(input())
count=0
A=list(map(int,input().split())) 
A.sort()
for k in range(N):
    find=A[k]
    i=0;j=N-1 #i는 리스트 첫번째, j는 리스트 마지막에 위치
    while i<j: #두 인덱스가 만나면 while 종료
        if A[i]+A[j]==find: # 두 수의 합이 찾는 수와 일치
            if i!=k and j!=k: #i,j는 k와 같은 위치가 되면 안됨
                count+=1
                break
            elif i==k : i+=1
            elif j==k: j-=1
        elif A[i]+ A[j] < find: #i를 증가시켜야 합의 수가 커짐
            i+=1
        elif A[i] + A[j] > find: #두 수의 합이 찾는수보다 크면 j 감소시켜야 합의 수 작아짐
            j-=1
print(count)

--> 강사님 수업 들으면서 바로바로 이해 못하겠어서 일단 타이핑은 하고 제출은 안함
--> 따로 풀어봐야할듯

백준(자습)

  • 백준 4344번 평균은 넘겠지

sum,avg,cnt=0,0,0
n=int(input())
for i in range(n):
    score=list(map(int,input().split()))
    for j in range(1,len(score)):
        sum+=score[j]
        avg=sum/score[0]
    for j in range(1,len(score)):
        if score[j]>avg:
            cnt+=1
    print(f'{cnt/score[0]*100:.3f}%')
    sum=0
    cnt=0

1) score에 list 형태로 인원+인원들의 점수 받아옴
2) 다음과 같이 구현했을 때 sum에 score 값 하나만 받아온 상태로 카운팅을 하니까 싹 다 평균보다 각각의 점수들이 높은 것 처럼 카운팅 되어버림

for j in range(1,len(score)):
        sum+=score[j]
        avg=sum/score[0]
        if score[j]>avg:
            cnt+=1

3) 따라서 for문을 2개 사용했고 sum에 score의 값이 다 더해진 상태에서 평균보다 큰 값들을 카운팅 함
4) 안쪽 for문을 for j in range(1,len(score)) 꼴로 구현한 이유는 score[0]은 인원 수가 들어오기 때문에 인원수를 제외한 점수들만 가지고 놀고 싶어서 다음과 같이 작성

  • 백준 4673번 셀프 넘버


def d(n):#원래 숫자 + 숫자의 각 자리수 ex)123 : 123 + 1 + 2 + 3
    selfnumber=n
    num=list(str(n))
    for i in range(len(num)):
        selfnumber+=int(num[i])
    return selfnumber

list1=list(range(1,10001))
for i in range(1,10001):
    if d(i) in list1:
        list1.remove(d(i))

for j in range(len(list1)):
    print(list1[j])

1) d(n) : 생성자 판별 함수 / 문제 설명을 보면 생성자 --> 123->123+1+2+3=129
--> 129 는 123의 생성자
2) d(n) : num에 입력받는 수를 list의 형태로 저장
3) 입력한값 += 각 자릿값 해서 생성자를 만듬
4) 만들어진 생성자 반환
5) list1 -> 1~10000 을 list 형태로 저장
6) for문을 10000까지 돌면서 1~10000 사이에 d(i) 즉 생성자가 있다면
7) 1~10000이 들어있는 list에서 해당 원소 삭제
8) list1 출력

  • 백준 1065번 한수


n=int(input())
cnt=0
for i in range(1,n+1):
    if i<100:#한자리/두자리 공차가2개가 아니라 비교 불가능. 
        cnt+=1#예제 입력 1입력->1출력이기에 한자리,두자리는 모두 카운팅
    else:#세자리
        m=list(map(int,str(i)))#ex)i가 123이면 m에 [1,2,3,4,5] 의 형태로 저장
        #m=list(str(123)) --> ['1','2','3'] 으로 저장됨을 유의
        if m[0]-m[1] == m[1]-m[2]:#세자리 기준으로 공차가 같다면
            cnt+=1#카운팅
print(cnt)

한수 : 각 자리수가 등차수열인 수 / 즉 공차가 같은 수
1) if i<100 : cnt+=1 -> 한자리/두자리수는 공차가 애초에 1개이기에 비교가 어려운데 예제입력 2를보면 1 입력 -> 1 출력 즉 한자리,두자리도 한수에 포함한다고 판단하여 다음과 같이 if문 작성
2) 세자리 숫자를 기준으로 m=list(map(int,str(i))) --> i가 123이면 m에 [1,2,3,4,5]의 형태로 저장
3) m=list(str(123)) -> ['1','2','3'] 의 형태로 저장됨을 유의 / 정수형으로 뽑아오고 싶다면 map 을 사용하여야 함.
4) if m[0]-m[1]==m[1]-m[2] : cnt+=1 --> 세자리 기준으로 공차가 같다면 카운팅
cf) 2,3번항목 아래 소스코드 참조

0개의 댓글