복붙노트

[PYTHON] 파이썬 : 0으로 나누기 주위에 점점

PYTHON

파이썬 : 0으로 나누기 주위에 점점

큰 데이터 세트의 부동 소수점 숫자가 있습니다. 나는 그들을 반복하고 각각에 대해 np.log (x)를 평가한다. 나는 얻다

RuntimeWarning: divide by zero encountered in log

이 오류가 발생하면이 문제를 해결하고 0으로 돌아가고 싶습니다.

나는 새로운 함수를 정의하려고 생각하고있다.

def safe_ln(x):
    #returns: ln(x) but replaces -inf with 0
    l = np.log(x)
    #if l = -inf:
    l = 0
    return result

기본적으로 출력이 "-inf"라는 테스트 방법이 필요하지만 진행 방법을 알지 못합니다. 도와 줘서 고마워!

해결법

  1. ==============================

    1.x = 0에 대한 로그는 무한대의 값을 가지므로 입력 값이 0인지 단순히 확인하고 원하는 값을 반환합니다.

    x = 0에 대한 로그는 무한대의 값을 가지므로 입력 값이 0인지 단순히 확인하고 원하는 값을 반환합니다.

    def safe_ln(x):
        if x <= 0:
            return 0
        return math.log(x)
    

    편집 : 작은 편집 : 당신은 0보다 작거나 같은 모든 값을 확인해야합니다.

    EDIT 2 : np.log는 numpy 배열로 계산하는 함수입니다. 단일 값의 경우 math.log를 사용해야합니다. 위의 함수가 numpy로 보이는 방식입니다.

    def safe_ln(x, minval=0.0000000001):
        return np.log(x.clip(min=minval))
    
  2. ==============================

    2.np 함수를 사용하고 있으므로 numpy 배열로 작업하고 있다고 추측 할 수 있습니까? 그런 다음이를 수행하는 가장 효율적인 방법은 for 루프 대신 where 함수를 사용하는 것입니다.

    np 함수를 사용하고 있으므로 numpy 배열로 작업하고 있다고 추측 할 수 있습니까? 그런 다음이를 수행하는 가장 효율적인 방법은 for 루프 대신 where 함수를 사용하는 것입니다.

    myarray= np.random.randint(10,size=10)
    result = np.where(myarray>0, np.log(myarray), 0)
    

    그렇지 않으면 단순히 로그 함수를 사용하여 구멍을 패치 할 수 있습니다.

    myarray= np.random.randint(10,size=10)
    result = np.log(myarray)
    result[result==-np.inf]=0
    

    np.log 함수는 0 값에서 사용될 때 정확하게 반환하므로 0을 반환 할 것입니까? 어딘가에 원래 값으로 되돌려 야한다면, 당신은 0으로 바뀌는 몇 가지 문제를 경험하게 될 것입니다 ...

  3. ==============================

    3.당신은 이것을 할 수 있습니다.

    당신은 이것을 할 수 있습니다.

    def safe_ln(x):
       try:
          l = np.log(x)
       except ZeroDivisionError:
          l = 0
       return l
    
  4. ==============================

    4.예외 처리 사용 :

    예외 처리 사용 :

    In [27]: def safe_ln(x):
        try:
            return math.log(x)
        except ValueError:       # np.log(x) might raise some other error though
            return float("-inf")
       ....:     
    
    In [28]: safe_ln(0)
    Out[28]: -inf
    
    In [29]: safe_ln(1)
    Out[29]: 0.0
    
    In [30]: safe_ln(-100)
    Out[30]: -inf
    
  5. ==============================

    5.너는 할 수 있었다 :

    너는 할 수 있었다 :

    def safe_ln(x):
        #returns: ln(x) but replaces -inf with 0
        try:
            l = np.log(x)
        except RunTimeWarning:
            l = 0
        return l
    
  6. ==============================

    6.Enrico가 제공 한 답변은 훌륭하지만 두 솔루션 모두 경고 메시지가 나타납니다.

    Enrico가 제공 한 답변은 훌륭하지만 두 솔루션 모두 경고 메시지가 나타납니다.

    RuntimeWarning: divide by zero encountered in log
    

    대안으로, 우리는 여전히 where 함수를 사용할 수 있지만 적절한 경우에만 주요 계산을 실행합니다 :

    # alternative implementation -- a bit more typing but avoids warnings.
    loc = np.where(myarray>0)
    result2 = np.zeros_like(myarray, dtype=float)
    result2[loc] =np.log(myarray[loc])
    
    # answer from Enrico...
    myarray= np.random.randint(10,size=10)
    result = np.where(myarray>0, np.log(myarray), 0)
    
    # check it is giving right solution:
    print(np.allclose(result, result2))
    

    제 유스 케이스는 부서 용 이었지만 원칙은 분명히 동일합니다.

    x = np.random.randint(10, size=10)
    divisor = np.ones(10,)
    divisor[3] = 0 # make one divisor invalid
    
    y = np.zeros_like(divisor, dtype=float)
    loc = np.where(divisor>0) # (or !=0 if your data could have -ve values)
    y[loc] = x[loc] / divisor[loc]
    
  7. from https://stackoverflow.com/questions/13497891/python-getting-around-division-by-zero by cc-by-sa and MIT license