Programming/Algorithm(Python)

Short Circuit Evaluation - 정해진 결말

code_wizard 2023. 12. 23. 20:28

알고리즘 bfs문제(2차원배열) 문제를 풀 때, index가 나가지 않도록 예외처리를 해야 한다.

이때

      move = [(0,-1),(0,1),(-1,0),(1,0)]

      for dx,dy in move:
            px = x + dx
            py = y + dy
            if 0<=px<N and 0<=py<M and mat[px][py]==0: # 나가지 않았고
            # if mat[px][py]==0: # 익지않은 토마토라면 
                mat[px][py] = 1 
                tomorrow_spread.append([px,py])

코드처럼

if 0 <=px <N and 0 <=py <M and mat [px][py]==0: # 나가지 않았고

px, py가 나간 값일 수도 있는데

한 번에 검사를 할 수 있을까? - (위 코드는 통과된 코드)

나갔다면 아래와 같이 "IndexError"가 발생해야 한다.

그 이유는

Short Circuit Evaluation 때문이다.


# Short Circuit Evaluation

편하게 숏서킷룰(short circuit rule)이라고 부르겠다.

숏서킷룰이란?

좌항만으로 and(&&)or(||) 연산 결과를 판별하는 기능

 

그림과 같이 and 연산을 하는데

좌항이 거짓이라면 어떻게 될까요?

이 논리연산자는 오른쪽에 물음표(?) 값을 볼 필요 없이 거짓이기 때문에

우항을 살펴볼 필요가 없습니다.

=> 따라서 좌항이 거짓이라면 우항도 보지 않고 정해진결말로 거짓입니다.

이는 or 연산자도 마찬가지로

좌항이 "참"이라면 우항도 볼 필요 없이 결과는 "참"입니다.

숏 서킷룰을 모른다면 아주 중요한 논리 오류를 낼 수도 있습니다.


# 논리오류 예시

https://www.acmicpc.net/problem/7576

 

7576번: 토마토

첫 줄에는 상자의 크기를 나타내는 두 정수 M,N이 주어진다. M은 상자의 가로 칸의 수, N은 상자의 세로 칸의 수를 나타낸다. 단, 2 ≤ M,N ≤ 1,000 이다. 둘째 줄부터는 하나의 상자에 저장된 토마토

www.acmicpc.net

 

백준 - 7576번 토마토문제를 참고하여 설명합니다.

<잘못된 접근> <올바른 접근>
def bfs():
  while today_spread:
      x, y = today_spread.pop()
      for dx,dy in move:
        px = x + dx
        py = y + dy
        if mat[px][py]==0 and 0<=px<N and 0<=py<M:
            mat[px][py] = 1
            tomorrow_spread.append([px,py])
def bfs():
 while today_spread:
    x, y = today_spread.pop()
    for dx,dy in move:
       px = x + dx
       py = y + dy
       if 0<=px<N and 0<=py<M and mat[px][py]==0:
           mat[px][py] = 1
           tomorrow_spread.append([px,py])

 

# 잘못된 접근 시

index에러가 발생하고,

 

# 올바른 접근 시

숏서킷룰을 올바르게 이행했기에

예외처리가 발생된 애들 중에서만 (참, 거짓)을 판단하기에 성공합니다.


# 결론

숏서킷룰을 고려하면 불필요한 연산을 줄여 실행속도(최적화)를 높일 수 있다.

but 논리오류를 고려한 숏서킷룰을 사용해야 한다.