Abstract

새로운 음성 인식 응용프로그램이 포함되는 순환 신경망 언어 모델(RNN LM)이 제공된다. 최첨단 backoff language 모델과 비교했을때, perplexity가 50%하는 결과가 나타났다. 음성인식 실험은 Wall Street Joural task에서 단어 오차율이 같은 양의 데이터로 학습된 모델과 비교했을 때 대략 18% 감소를 보여준다. 그리고 대락 RNN LM보다 더 많은 데이터로 학습된 backoff 모델의 오차율에서 대략 5% 감소했다. 우리는 높은 계산(훈련) 복잡성을 제외하고, 연결론적 언어 모델이 표준 n-gram 기술보다 뛰어나다는 것을 말하는 충분한 경험적 증거를 제시한다.

index Terms : language modeling, recurrent neural networks, speech recognition

Introduction

시퀀셜 데이터 예측은 머신러닝과 인공지능에서 많은 key problem을 가지고 있다고 여겨진다. statistical language modeling의 목표는 문맥을 가진 텍스트 데이터에서 다음 단어를 예측하는 것이다. 따라서, 우리는 언어 모델을 구성할 때, 시퀀셜 데이터 예측 문제를 다룰 것이다. 그럼에도 불고하고, 이러한 통계 모델을 넘으려는 많은 시도는 매우 특정한 언어 도메인의 접근 방식을 포함한다.

예를 들어, 자연어 문장이 구문 분석 트리에 의해 설명될 수 있다는 가정, 또는 단어, 구문, 의미의 형태를 고려해야할 수 있다는 가정.

심지어 가장 널리 일반적으로 사용되는 모델(n-gram 통계에 기반한)도 언어는 원자 기호, 즉 문장을 형성하는 단어로 구성된다고 가정한다. 그리고 문장의 끝 기호가 중요하고 특별한 역할을 한다.

simple n-gram 모델에 비해 언어 모델링이 눈에 띄는 과정이 있었는지 의문이다. 만약 우리가 시퀀셜 데이터를 더 잘 예측하는 모델의 능력에 의해 이러한 진행상황을 측정한다면, 대답은 캐시 모델과 클래스 기반 모델의 도입에 상당한 개션이 이뤄졌다는 것이다. 다른 많은 기술들이 목적을 이루는 동안, 노력의 대부분은 비슷한 캐쉬 모델(긴 문맥 정보를 설명하는 모델) 혹은 클래스 기반 모델(비슷한 단어간에 파라미터를 공유하여 짧은 context에 대한 매개 변수 추정을 개선함.)

실제로 응용 프로그램을 통해 고급 언어 모델링 기술의 성공을 측정하려면 훨씬 더 회의적이어야 할 것이다. 실제 음성 인식 또는 기계 번역 시스템을 위한 언어 모델은 엄청난 양의 데이터를 기반으로 구축되며, 일반적인 믿음은 더 많은 데이터가 우리에게 필요한 전부라고 말한다. 연구에서 도출된 모델은 복잡한 경향이 있으며 종종 매우 제한된 양의 훈련 데이터를 기반으로 하는 시스템에서만 잘 작동한다. 실제로 제안된 대부분의 고급 언어 모델링 기술은 단순한 기준선에 비해 아주 작은 개선 사항만 제공하며 실제로 거의 사용되지 않는다.

Model description

순차 데이터를 모델링하기 위해 반복 신경망에 대해 조사하기로 결정했다. 통계 언어 모델링에서 인공 신경망을 사용하는 것은 고정된 길이 컨텍스트를 가진 feedforward 신경망을 사용한 Bengio에 의해 이미 제안됐다. 이 접근 방식은 예외적으로 성공적이었으며 Goodman의 추가 조사를 통해 이 단일 모델이 클래스 기반 모델을 포함한 다른 기술을 기반으로 한 여러 모델의 혼합보다 성능이 우수하다는 것을 알 수 있다. 이후, Schwenk는 신경망 기반 모델이 양호한 기준선 시스템에 대한 몇 가지 작업에 대해 음성 인식의 상당한 향상을 제공한다는 것을 보여주었다.

Bengio 접근 방식의 주요 결점은 feedforward 네트워크가 훈련 전에 특별하게 지정되어야하는 고정된 길이의 컨텍스트를 사용해야 한다는 것이다. 보통 이것은 신경망이 다음 단어를 예측할 때 5개에서 10개의 단어만 본다는 것을 의미한다. 인간이 더 긴 문맥을 성공적으로 이용할 수 있다는 것은 잘 알려져 있다. 또한 캐시 모델은 신경망 모델에 보완 정보를 제공하므로 임의의 길이를 가진 컨텍스트에 대해 시간 정보를 암시적으로 인코딩하는 모델을 생각하는 것은 당연하다.

반복 신경망은 제한된 크기의 컨텍스트를 사용하지 않는다. 반복적인 연결을 사용함으로써, 정보는 임의로 오랜 시간 동안 이러한 네트워크 내부에서 순환할 수 있다. 하지만, 확률적 경사 하강에 의한 long-term dependencies를 학습하는 것은 상당히 여려울 수 있다는 주장도 종종 제기된다.

우리의 연구에서, 우리는 보통 단순 반복 신경망 또는 Elman 네트워크라고 불리는 아키텍처를 사용했다. 이것은 아마도 반복 신경망의 가장 단순한 버전일 것이며 구현과 훈련이 매우 쉽다. 네트워크에는 입력 계층 x, 숨겨진 계층 s(context layer 또는 state) 및 출력 계층 y가 있다. 시간 t로 입력은 x(t), 출력은 y(t), 히든 레이어는 s(t)로 나타낸다. 입력 벡터 x(t)는 현재 단어를 나타내는 벡터 w와 시간 t-1에서 컨텍스트 레이어의 s의 뉴런 출력값을 연결하여 형성된다. input, hidden, output layer는 다음과 같이 계산된다.

 

함수 $f(z)$는 시그모이드 활성화 함수로 아래와 같다.

 

함수 $g(z)$는 소프트맥스 함수로 아래와 같다.

 

초기화의 경우 s(0)은 많은 양의 데이터를 처리할 때 초기화는 중요하지 않은 0.1과 같이 작은 값의 벡터로 설정될 수 있다. 다음 시간 단계에서 s(t+1)는 s(t)의 사본이다. 입력 벡터 x(t)는 N 코드화 1(one-hot 인코딩)을 사용하여 인코딩된 단어 t를 나타내며 벡터 x의 이전 컨텍스트 레이어 크기는 사전 V의 크기와 같다.(실제로 30,000 ~ 200,000). 컨텍스트(hidden) 레이어의 크기는 일반적으로 30 ~ 500 hidden 단위이다. 우리의 실험에 따르면, hidden 레이어의 크기는 훈련 데이터의 양을 반영해야 한다. 많은 양의 경우

네트워크는 훈련 말뭉치의 모든 데이터가 순차적으로 표시되는 여러 epoch에서 훈련된다. 가중치는 작은 값으로 초기화 된다.(평균이 0이고 분산이 0.1인 랜덤 가우시안 노이즈로) 네트워크를 훈련시키기 위해 확률적 경사 하강을 가진 backpropagation 알고리즘을 사용한다. 시작 학습률은 α = 0.1입니다. 각 epoch 이후, 네트워크는 유효성 검사 데이터에 대해 테스트된다. 검증 데이터의 로그-라이클리후드가 증가하면 새로운 epoch에서도 학습을 계속한다. 유의미한 개선이 보이지 않으면, 학습률 $\alpha$는 새로운 epoch가 시작할 때마다 절반으로 감소한다. 다시 이렇다할 개선이 없으면 훈련이 끝난다. 수렴은 보통 10~20 epoch 후에 이뤄진다.

우리의 실험에서, 네트워크는 매우 큰 hidden 레이어를 사용하더라도 크게 오베트레이닝되지 않는다. (- 큰 가중치에 불이익을 주기 위한 네트워크의 정규화는 큰 개선을 제공하지 않았다.) 출력 계층 y(t)는 이전단어 w(t)와 컨텍스트(t-1)가 주어진 다음 단어의 확률 분포를 나타낸다. 소프트맥스는 이 확률 분포가 유효한지 확인하다.

 

각 교육 단계에서 교차 엔트로피 기준에 따라 오류 벡터가 계산되고 backpropagation 알고리즘으로 가중치가 업데이트 된다. $error(t)=desired(t)-y(t)$

desired는 1-of-N 코딩 표현을 사용한 벡터로 특정 컨텍스트에서 예측되는 단어를 나타내고 y(t)는 실제 네트워크로부터의 출력이다.

통계적 언어 모델링의 훈련 단계와 시험 단계는 일반적으로 시험 데이터가 처리될 때 모델이 업데이트되지 않는다는 점에서 다르다. 따라서, 새로운 사람 이름이 테스트 세트에서 반복적으로 발생한다면, 알려진 단어로 구성되더라도 반복적으로 매우 작은 확률을 얻게 될 것이다. 이러한 long term 메모리는 컨텍스트 유닉의 활성화(이러한 매우 빠르게 변화함에 따라)가 아니라 시냅스 자체에 있어야 하며, 네트워크가 테스트 단계 중에도 훈련을 계속해야 한다고 가정할 수 있다. 우리는 그러한 모델을 동적 모델이라고 부른다. 동적 모델의 경우 고정 학습 속도 α = 0.1을 사용한다. 학습 단계에서는 모든 데이터가 epoch에서 여러 번 네트워크에 제공되지만, 동적 모델은 테스트 데이터를 처리할 때 한 번만 업데이트된다. 이것은 물론 최적의 솔루션은 아니지만, 우리가 볼 수 있듯이 정적 모델에 대한 큰 난이도 감소를 얻기에 충분하다. 이러한 수정은 신경 네트워크가 연속 공간에서 학습하는 차이와 함께 backoff 모델의 캐시 기법과 매우 유사하므로, '개'와 '고양이'가 관련이 있는 경우, 테스트 데이터에서 '개'가 자주 발생하는 것도 '고양이'의 확률을 높일 수 있다는 점에 유의한다.

따라서 동적으로 업데이트된 모델은 새로운 도메인에 자동으로 적응할 수 있다. 그러나 음성 인식 실험에서 역사는 인식자에 의해 주어진 가설로 표현되며 인식 오류를 포함한다. 이는 일반적으로 ASR에서 캐시 n-gram 모델의 성능 저하를 초래한다.

여기서 설명하는 학습 알고리즘은 τ = 1을 사용한 시간 경과에 따른 잘린 backpropagation라고도 한다. 현재 시간 단계에 대해서만 계산된 오류 벡터를 기반으로 네트워크의 가중치가 업데이트되기 때문에 최적화되지 않는다. 이러한 단순화를 극복하기 위해 BPTT(Back Propagation through Time) 알고리즘이 일반적으로 사용된다.

Bengio와 schwenk에서 사용하는 feedforward 신경망과 반복 신경망 사이의 주요 차이점 중 하나는 훈련 전에 조정하거나 특별하게 선택해야 하는 매개 변수의 양이다. RNN LM의 경우 hidden(컨텍스트) 계층의 크기만 선택하면 된다. feedforward 네트워크의 경우 단어를 저차원 공간에 투영하는 계층의 크기, 숨겨진 계층의 크기 및 컨텍스트 길이를 조정해야한다.

Optimization

성능을 향상시키기 위해, 우리는 (훈련 텍스트에서) 임계값(threshold)보다 적게 발생하는 모든 단어를 특별한 rare 토큰으로 병합한다. 단어-확률(Word-probabilities) 계산은 아래와 같다.

 

 

여기서 $C_{rare}$는 단어에서 임계값보다 적게 발생하는 단어 수입니다. 따라서 모든 rare 단어는 동등하게 취급된다. 즉, 확률은 균일하게 분배된다. Schwenk는 추가적인 성능 향상에 사용할 수 있는 몇 가지 접근 방식을 설명한다. 추가 가능성은 [10][11][12]에서도 논의되며, 대부분의 가능성을 RNN에도 적용할 수 있다. 비교를 위해, 우리의 기본 구현이 브라운 말뭉치(800K 단어, 100개의 숨겨진 단위 및 어휘 임계값(vocabulary threshold 5)를 기반으로 RNN 모델을 훈련하는 데 약 6시간이 소요되며, Bengio는 유사한 데이터와 신경망 크기를 사용할 때 기본 구현에 113일, 중요도 샘플링 [10]으로 26시간을 걸렸다고 보고서에 썼다. 계산 속도를 올리기 위해 BLAS 라이브러리를 사용한다.

Conclusion and future work

반복 신경망은 모든 실험에서 최첨단 backoff 모델보다 훨씬 더 많은 데이터에 대해 backoff 모델을 훈련한 경우에도 훨씬 더 우수한 성능을 보였다. WSJ 실험에서는 동일한 양의 데이터에 대해 훈련된 모델의 경우 워드 오류율 감소가 약 18%, 백오프 모델이 5번 훈련되었을 때 12%이다. RNN 모델보다 데이터 수가 더 많습니다. NIST RT05의 경우, 우리는 모델이 단 5번에 대해 훈련되었다고 결론을 내릴 수 있다. 5.4백만 단어의 도메인 내 데이터는 수백 배 많은 데이터에 대해 훈련된 빅 backoff 모델을 능가할 수 있습니다. 언어 모델링은 단지 n-gram(n-gram)의 계산에 관한 것이며, 결과를 개선하는 유일한 합리적인 방법은 새로운 훈련 데이터를 획득 하는 것이라는 속설을 깨는 결과이다.

표 2에 보고된 난해성 개선은 온라인 학습의 매우 중요한 효과(본 논문에서는 동적 모델이라고도 하며 비지도 LM 훈련 기법과 매우 유사한 음성인식 맥락에서)와 유사한 데이터 세트에 대해 보고된 최대 중 하나이다. WER은 약간만 영향을 받고 정확한 테스트 데이터 순서가 필요하지만, 온라인 학습은 캐시와 트리거 같은 정보를 얻는 자연스러운 방법을 제공하므로 더 자세히 조사해야한다.(데이터 압축의 경우, 예를 들어, 예측 신경망 훈련을 위한 온라인 기술은 이미 Mahoney에 의해 연구되었다.) 언어를 실제로 배울 수 있는 모델을 구축하려면 온라인 학습이 매우 중요합니다. 새로운 정보를 얻는 것은 확실히 중요합니다. 반복 신경망 학습을 위한 시간 알고리즘을 통한 역전파에 대한 추가 조사가 추가적인 개선을 제공할 수 있다. 장난감 작업에 대한 예비 결과는 유망하다. 그러나 캐시 모델은 BPTT로 훈련된 동적 모델에까지 여전히 보완 정보를 제공하기 때문에 단순한 반복 신경망은 정말 긴 컨텍스트 정보를 캡쳐할 수 있는 것 같지는 않다. 설명은 [6]에서 논의한다.

task에서 task 또는 언어별 가정을 하지 않았기 때문에 기계번역이나 OCR과 같은 backoff 언어 모델을 사용하는 모든 종류의 애플리케이션에서 RNN 기반 모델을 거의 쉽게 사용할 수 있다. 특히, [12]에서 이미 설명한 것처럼, 큰 어휘를 가진 변곡 언어 또는 언어를 포함하는 작업은 NN 기반 모델을 사용함으로써 이득을 얻을 수 있다.

연구에서 보고된 매우 좋은 결과 외에도, 제안된 반복 신경망 모델은 언어 모델링을 기계 학습, 데이터 압축 및 인지 과학 연구와 더 밀접하게 연결하기 때문에 흥미롭다. 앞으로 이러한 connection이 더 잘 이해되기를 바란다.

논문 리뷰

전반적으로 n-gram에서 진화했다는 것에 초점을 맞춘 논문 같다. 내가 느낀 바로는 사람은 단어를 무한히 듣고 답할 수 있는데 n-gram 모델은 제한적인 입력을 받는 것으로 이거를 까려고? 만든 논문이라는 느낌이다. 핵심으로는 BPTT를 사용했다는 것과 semantic semantic utterance meaning으로 vocabulary에 없는 단어가 들어왔을때도 비슷한 단어를 찾아 결과를 낸다는 것 같다.

글을 시작하며

이전에 작성한 Numpy에 이어서 작성하는 글입니다. 이전 글을 보고 싶으신 분은 아래 링크를 눌러 확인해주세요😁

2021/02/07 - [인공지능 공부/이론 및 파이썬] - [이론 및 파이썬] Numpy(1)

 

[이론 및 파이썬] Numpy(1)

글을 시작하며 부스트캠프에서 수업을 한 Numpy부분을 정리하고 공부하기 위해서 작성합니당 계속 하는데 잘 까먹는다...하면서 글을 시작!😂 Numpy란? Numerical Python 파이썬의 고성능 과학 계산용

hwanii-with.tistory.com

 

Operation Function

sum : ndarray의 element들 간의 합을 구함

axis : 모든 operation function을 실행할 때 기준이 되는 dimension 축

mean & std : ndarray의 element들 간의 평균 또는 표준 편차를 반환

그 외에도 다양한 수학 연산자를 제공함.

concatenate : numpy array를 합치는(붙이는 함수)

 

np.newaxis 하면 축이 하나 추가가 됨.

import numpy as np

a = np.array([[1,2],[3,4]])
b = np.array([5,6])
b = b[np.newaxis, :]
b
# array([[5, 6]])
np.concatenate((a,b.T), axis=1) # T는 transpose
# array([[1, 2, 5],
#       [3, 4, 6]])

 

Array Operations

array간의 기본적인 사칙 연산을 지원함.

S

Element-wise operations

  • Array간 shape이 같을 때 일어나는 연산.

Dot product

  • Matrix의 기본 연산, dot 함수 사용. 
  • 2dimension에서 내적

 

broadcasing : Shape이 다른 배열 간 연산을 지원하는 기능

 

Scaler - vector 외에도 vector- matrix 간의 연산도 지원

 

Numpy와 for loop 속도차이

  • 일반적으로 속도는 다음과 같다.
  • for loop < list comprehension < numpy
  • 100,000,000 번의 loop이 돌 때, 약 4배 이상의 성능 차이를 보임
  • Numpy는 C로 구현되어 있어, 성능을 확보하는 대신 파이썬의 가장 큰 특징인 dynamic typing을 포기함
  • 대용량 계산에서는 가장 흔히 사용됨
  • Concatenate처럼 계산이 아닌, 할당에서는 연산 속도의 이점이 없음.
def sclar_vector_product(scalar, vector):
	result = []
	for value in vector:
		result.append(scalar * value)
	return result


iternation_max = 100000000
vector = list(range(iternation_max))
scalar = 2

%timeit sclar_vector_product(scalar, vector) # for loop을 이용한 성능
%timeit [scalar * value for value in range(iternation_max)]
# list comprehension을 이용한 성능
%timeit np.arange(iternation_max) * scalar # numpy를 이용한 성능

# 21.9 s ± 927 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)
# 16.6 s ± 104 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)
# 450 ms ± 46.2 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)

 

Comparision

All & any

import numpy as np

a = np.arange(10)
a < 4
#array([ True,  True,  True,  True, False, False, False, False, False,False])

np.any(a>5), np.any(a<0)
# (True, False)
np.all(a>5), np.all(a < 10)
# (False, True)

 

numpy는 배열의 크기가 동일 할 때 element간 비교의 결과를 Boolean type으로 반환

test_a = np.array([1, 3, 0], float)
test_b = np.array([5, 2, 1], float)

test_a > test_b
# array([False,  True, False])

 

np.where

a = np.arange(10)
np.where(a > 5, 3, 2)  # where(condition, TRUE, FALSE)
# array([2, 2, 2, 2, 2, 2, 3, 3, 3, 3])
np.where(a > 5) # 인덱스 값이 나옴
# (array([6, 7, 8, 9], dtype=int64),) 

a = np.array([1, np.NaN, np.Inf], float)
np.isnan(a) # 메모리의 값이 존재하지 않는 경우
# array([False,  True, False])
np.isfinite(a) # 한정되지 않는 값.
# array([ True, False, False])

 

argmax & argmin

a = np.array([1, 2, 4, 5, 8, 78, 23, 3])
a.argsort()
# array(0,1,7,2,3,4,6,5])
a.argsort()[::-1]
# array([5, 6, 4, 3, 2, 7, 1, 0], dtype=int64)

np.argmax(a), np.argmin(a)
# (5, 0)

a = np.array([[1, 2, 4, 7], [9, 88, 6, 45], [9, 76, 3, 4]])
np.argmax(a, axis=1), np.argmin(a, axis=0)
# (array([3, 1, 1], dtype=int64), array([0, 0, 2, 2], dtype=int64))

 

boolean index

test_array = np.array([1, 4, 0, 2, 3, 8, 9, 7], float)
test_array > 3
# array([False,  True, False, False, False,  True,  True,  True])
test_array[test_array > 3]
# array([4., 8., 9., 7.])

 

fancy index

a = np.array([2, 4, 6, 8], float)
b = np.array([0,0,1,3,2,1],int)

a[b]

a.take(b)  # take 함수: bracket index와 같은 효과
# array([2., 2., 4., 8., 6., 4.])

boolean index는 원래 index의 shape이 같아야하지만 fancy index는 같을 필요는 없음. 하지만 index범위 안에 있어야함.

 

numpy data i/o

  • text type의 데이터를 읽고, 저장하는 기능
a = np.loadtxt("./poppulations.txt",delimiter="\t")

a_int = a.astype(int)

np.savetxt('int_data.csv', a)int, delimiter=",")

주로 npy파일로 저장함.

pandas 연습하기 좋은 자료 링크

 

Pandas Exercises, Practice, Solution - w3resource

Pandas Exercises, Practice, Solution: pandas is a Python package providing fast, flexible, and expressive data structures designed to make working with relational or labeled data both easy and intuitive.

www.w3resource.com

 

Excellent Pandas Exercise to Learn Pandas | Data Science and Machine Learning

Excellent Pandas Exercise to Learn Pandas.

www.kaggle.com

 

guipsamora/pandas_exercises

Practice your pandas skills! Contribute to guipsamora/pandas_exercises development by creating an account on GitHub.

github.com

pandas 공부에 도움되는 책

  • 머신러닝 탐구생활
 

머신러닝 탐구생활 : 네이버 책검색

'머신러닝 탐구생활'의 네이버 책검색 결과입니다.

m.search.naver.com

  • 파이썬 라이브러리를 활용한 데이터 분석
 

파이썬 라이브러리 : 네이버 책검색

'파이썬 라이브러리'의 네이버 책검색 결과입니다.

m.search.naver.com

 

글을 시작하며

부스트캠프에서 수업을 한 Numpy부분을 정리하고 공부하기 위해서 작성합니당

계속 하는데 잘 까먹는다...하면서 글을 시작!😂

 

Numpy란?

  • Numerical Python
  • 파이썬의 고성능 과학 계산용 패키지
  • Matrix와 Vector와 같은 Array 연산의 사실상의 표준
  • 한글로 넘파이로 주로 통칭
  • 일반 List에 비해 빠르고, 메모리 효율적
  • 반복문 없이 데이터 배열에 대한 처리를 지원함
  • 선형대수와 관련된 다양한 기능을 제공함
  • c, c++, 포트란 등의 언어와 통합가능

ndarray

import numpy as np

test_array = np.array([1, 4, 5, 8], float)
print(test_array)
type(test_array[3])

# [1. 4. 5. 8.]
# numpy.float64
  • numpy는 np.array 함수를 활용 배열을 생성함. → ndarray(객체)
  • numpy는 하나의 데이터 type만 배열에 넣을 수 있음.
  • List와 가장 큰 차이점 → dynamic typing not supported
  • C의 Array를 사용하여 배열을 생성함.
  • numpy array는 차례대로 값이 저장되는 반면 파이썬의 List는 값의 주소값을 List에 넣어서 2번 들어가는 방식이다.(-5 ~ 256은 고정 주소값)
  • 타입도 일정하기 때문에 메모리도 효율적이다.
test_array = np.array([1, 4, 5, "8"], float) # String Type의 데이터를 입력해도

print(test_array)
print(type(test_array[3])) # Float Type으로 자동 형변환을 실시
print(test_array.dtype) # Array(배열) 전체의 데이터 Type을 반환함
print(test_array.shape) # Array(배열) 의 shape을 반환함
print(test_array.nbytes) # ndarry object의 메모리 크기를 반환함.

# [1. 4. 5. 8.]
# <class 'numpy.float64'>
# float64
# (4,)
# 32  -> float64는 8bytes 이므로  4 * 8 = 32

 

numpy Rank

 

Hadling Shape

reshape : Array의 shape의 크기를 변경함, element의 갯수는 동일

  • reshape에서 (-1, n) 하면 n으로 지정하고 나머지 사이즈에 맞춰서 넣어진다.
  • ex : (2,4)를 reshape(-1,2) 하면 reshape(4,2)와 같다.

flatten : 다차원 array를 1차원 array로 변환.

ravel : 다차원 array를 1차원 array로 변환.

a = np.array([[1,2,3,4],[5,6,7,8]])

a1 = a.flatten()
a2 = a.ravel()
a3 = a.reshape(-1)

# array([1, 2, 3, 4, 5, 6, 7, 8])
# array([1, 2, 3, 4, 5, 6, 7, 8])
# array([1, 2, 3, 4, 5, 6, 7, 8])

a[0][0] = 100
a

# array([[100,   2,   3,   4],
#       [  5,   6,   7,   8]])

a1
# array([1, 2, 3, 4, 5, 6, 7, 8])
a2
# array([100,   2,   3,   4,   5,   6,   7,   8])
a3
# array([100,   2,   3,   4,   5,   6,   7,   8])

 

위에서 보이는 것처럼 reshape과 flatten, reval로 1차원으로 만들 수 있습니다. 각각의 함수에 차이점이 있다면 아래와 같습니다.

numpy.ravel() numpy.reshape() numpy.ndarray.flatten()
1차원배열(contiguous flattened array)반환 데이터 변경 없이 형상만 변경하여 반환 1차원배열 복사본을 반환
원본 값 변경시 같이 변함 원본 값 변경시 같이 변함 원본 값 변경시 변하지 않음.

Indexing & Slicing

index : List와 달리 이차원 배열에서 [0,0]표기법을 제공함.

  • matrix 일 경우 앞은 row, 뒤는 column을 의미함.

slicing : List와 달리 행과 열 부분을 나눠서 slicing이 가능함.

  • matrix의 부분 집합을 추출할 때 유용함.
a = np.array([[1, 2, 3, 4, 5], [6, 7, 8, 9, 10]], int)

a[:,2:] # 전체 Row의 2열 이상
a[1,1:3] # 1 Row의 1열 ~ 2열
a[1:3] # 1 Row ~ 2Row의 전체

Create Function

arange : array의 범위를 지정하여, 값의 list를 생성하는 명령어

np.array(30) # List의 range와 같음.
np.arange(0,5,0.5)  # (시작, 끝, step
np.arrange(30).reshpae(5,6)

zeros : 0으로 가득찬 ndarray 생성 np.zeros(shape, dtype, order)

ones : 1로 가득찬 ndarray 생성

empty : shape만 주어지고 비어있는 ndarray 생성 (memory initialization이 되지 않음)

something_list : 기존 ndarray의 shape 크기 만큼 1, 0 또는 empty array를 반환

identity : 단위행렬(i행렬)을 생성함.

eye : 대각선이 1인 행렬, k값의 시작 index의 변경이 가능.

diag : 대각 행렬의 값을 추출함.

random sampling : 데이터 분포에 따른 sampling으로 array를 생성 (시작, 끝, 개수)

글을 시작하며

부스트캠프 수업을 들으면서 확률 관련 용어에 대한 개념이 부족해 글을 작성했습니다.😥

수업에 열심히 따라가자..!

글의 순서는 다음과 같습니다

  1. 확률변수
  2. 이산형 확률변수와 이산형 확률 분포
  3. 연속형 확률변수와 연속형 확룔 분포

확률변수

표본공간과 확률변수 이야기 전에 확률실험과 표본공간에 대해서 이야기 하겠습니다.

  • 확률 실험 : 같은 조건 하에서 실험을 반복할 때, 그 결과가 예측 불가능한 실험
  • 표본 공간 : 확률 실험의 모든 가능한 결과들의 집합.

통계 이론에서 확률실험은 중요한 용어입니다. 확률실험은 예를 들어 주사위 던지기부터 시작해서, 모든 일상생활을 확률실험이라고 할 수 있습니다. 여기서 표본 공간은 확률 실험의 모든 가능한 결과들의 집합입니다.

그러면 본격적으로 표본공간과 확률변수를 이야기하겠습니다.

 

확률변수(Random Variable)

발생 가능한 모든 경우에 대해서 각각의 실숫값을 대입해주는 하나의 함수입니다.

표본공간의 각 원소 하나하나에 원하는 목적에 따라 그에 걸맞은 실수를 대입해주는 함수입니다.

확률변수는 변수의 척도(이산형, 연속형)에 따라 2가지로 나뉩니다.

 

이산형 확률변수와 연속형 확률변수

이산형 확률 변수(Discrete random variable)

  • 어떤 값을 가질 확률을 계산하는 확률변수
  • 확률 변수 X가 가질 수 있는 값이 유한이거나 셀 수 있는 경우
  • 예를 들어 동전 던지기나 주사위 던지기 등 계수 자료에 해당

연속형 확률변수(Continuous Random Variable)

  • 어떤 구간 내에 포함될 확률을 계산하는 확률변수
  • 데이터 공간에 정의된 확률변수의 밀도(density) 위에서의 적분을 통해 모델링.
  • 확률변수 x의 범위는 -무한부터 +무한까지.

 

지금까지 헷갈렸던 것은 확률변수와 확률 분포다.

이산형 확률변수와 연속형 확률변수는 모두 확률변수로 위에서 언급한 대로 변수의 척도에 따라서 나눈 것이다. 확률 변수는 위의 식들에서 모두 X이다.

 

확률 분포를 이제 설명하겠습니다.

 

확률 분포

  • 확률 변수가 특정한 값을 가질 확률을 나타내는 함수.
  • 예를 들어, 주사위를 던졌을 때 나오는 눈에 대한 확률변수가 있을 때, 그 변수의 확률분포는 이산형 확률 분포다.
  • 확률 변수가 어떤 종류의 값을 가지는가에 따라서 이산 확률 분포와 연속 확률 분포 중 하나에 속함.

 

이산형 확률 분포

  • 이산형 확률변수가 가지고 있는 확률의 구조를 의미.
  • 다른 말로는 확률질량함수(Probablity Maxx Function, pmf)라고 함.
  • 확률 질량 함수 : 이산 확률 변수에서 특정 값에 대한 확률을 나타내는 함수.
  • 대표적인 예로는 이산균등분포, 푸아송 분포, 베르누이 분포, 이항 분포 등이 있다.

동전으로 예를 들면 다음과 같다.

 

연속형 확률 분포

  • 확률 밀도 함수를 이용해 분포를 표현할 수있는 경우
  • 만일 모든 실수 x(즉, -무한부터 +무한까지)에 대해 음이 아닌 함수 f가 존재하여, 임의의 실수의 집합 B에 대해 다음을 만족하면 X를 만족하면., X를 연속형 확률변수라 함.
  • 대표적인 예료는 정규 분포, 연속균등분포, 카이제곱 분포 등이 있다.

 

그렇다면 확률 밀도 함수는 무엇인가?

 

확률 밀도 함수(probability density function)는 확률 변수의 분포를 나타내는 함수입니다.

확률 밀도 함수를 적분한 값이 확률로 확률 밀도 함수 자체가 확률이 아닙니다.

연속형 확률 변수가 어떤 특정 값을 가질 수 있는 확률이 0이라는 것도 정의에 따라서 풀면 다음과 같습니다.

여기서 delta x를 0으로 수렴하게 되므로 적분값이 0이 됩니다. 따라서 연속형 확률변수 X가 어떤 특정 값을 가질 수 있는 확률은 0입니다.

 

다시 한번 정의를 해보면 확률 밀도 함수 f(x)와 구간[a,b]에 대해서 확률 변수 X가 구간에 포함될 확률 P(a<=X<=b)는 아래와 같습니다.

 

왜 확률 질량 함수, 확률 밀도 함수라는 붙은걸까?

이산확률변수의 확률분포를 나타내는 것이 확률질량함수고, 연속확률변수의 확률을 결정하는 함수는 확률밀도함수라고 위에서 설명했었다. 그런데 여기서 왜 '질량'이란 단어와 '밀도'라는 단어가 쓰이게 되었을까?

 

우선 확률밀도함수 f(x)의 구간 x1에서 x2의 정적분을 생각해보자.

여기서 좌변은 [확률]이다. 그리고 우변에서 는 [구간길이]다. 그러면 의 단위는 [확률/구간길이]를 의미한다고 볼 수 있다. 왜냐하면 [확률/구간길이] x [구간길이] = [확률]이기 때문이다. 확률을 일종의 양(질량)으로 보고, 구간길이를 일종의 부피로 본다면, [확률/구간길이]는 [질량/부피]가 되므로 '밀도'를 의미하게 된다. 밀도는 단위 부피당 질량이기 때문이다. 따라서 는 '확률밀도함수'가 되는 것이다.

 

반면 이산확률변수 X의 경우 공식1과 같이 X의 값에 따라 각각 확률(질량)을 나타낼 수 있으므로, 를 확률질량함수라고 부르는 것이다.

 

참고 사이트

 

확률질량함수와 확률밀도함수 (왜 질량과 밀도??)

확률질량함수 확률질량함수(probability mass function, PMF)는 이산확률변수의 확률분포를 나타내는 함수이다. 즉, 확률변수가 취할 수 있는 값이 유한개이거나 자연수와 같이 셀 수 있는 이산확률변

bskyvision.com

 

 

위키독스

온라인 책을 제작 공유하는 플랫폼 서비스

wikidocs.net

 

 

Story 7.1 [연속형] 연속형확률변수

이 전 포스트까진 이산형 확률변수의 개념, 이산형 확률분포의 평균과 분산의 정의, 이산형 확률분포의 종...

blog.naver.com

 

 

확률 분포 - 위키백과, 우리 모두의 백과사전

위키백과, 우리 모두의 백과사전.

ko.wikipedia.org

 

글을 시작하며..

글의 순서

  1. Norm 이란?
  2. L1 Norm
  3. L2 Norm
  4. L1 Norm과 L2 Norm의 차이

 

Norm이란?

Norm은 크기의 일반화로 벡터의 크기(혹은 길이)를 측정하는 방법입니다. 두 벡터 사이의 거리를 측정하는 방법이기도 합니다.

여기서 p는 Norm의 차수를 의미. p = 1이면 L1 Norm. p = 2이면 L2 Norm. n은 해당 벡터의 원소 수.

 

L1 Norm

L1 Norm은 p가 1인 Norm입니다. 공식은 아래와 같습니다.

L1 Norm은 맨허튼 노름(Manhattan norm)이라고도 합니다. L1 Norm은 벡터의 요소에 대한 절댓값의 합입니다.

L1 Norm은 다음과 같은 영역에서 사용됩니다.

  • L1 Regularization
  • Computer Vision

계산되는 방식은 아래와 같습니다.

 

L2 Norm

L2Norm은 p가 2인 Norm입니다. L2 Norm은 n차원 좌표 평면(유클리드 공간(에서의 벡터의 크기를 계산하기 때문에 유클리드 노름(Euclidean norm)이라고도 합니다. L2 Norm은 피타고라스 정리를 활용한 것으로 공식은 아래와 같습니다.

L2 Norm은 다음과 같은 영역에서 사용됩니다.

  • L2 Regularization
  • KNN 알고리즘
  • kmean 알고리즘

계산되는 방식은 아래와 같습니다.

 

L1 Norm과 L2 Norm의 차이

검정색 두 점 사이의 L1 Norm은 빨간색, 파란색, 노란색 선으로 표현될 수 있고, L2 Norm은 오직 초록색 선으로만 표현될 수 있습니다. L1 Norm은 여러 가지 path를 가지지만 L2 Norm은 Unique shortest path를 가집니다.

 

L1 Norm과 L2 Norm을 시각화하면 아래와 같습니다.

이로 인해 L1 Loss와 L2 Loss의 차이가 발생합니다.

대표적으로는 L1 Loss는 0인 지점에서 미분이 불가능하다는 점이고 추가적으로 L1 Loss가 L2 Loss에 비해 Outlier에 대하여 더 Robust(덜 만감 혹은 둔감) 하다고 표현합니다.

 

아래는 L1 Norm과 L2 Norm의 코드입니다.

def l1_norm(x):
	x_norm = np.abs(x)
	x_norm = np.sum(x_norm)
	return x_norm

def l2_norm(x):
	x_norm = x * x
	x_norm = np.sum(x_norm)
	x_norm = np.sqrt(x_norm)
	return x_norm

정규 표현식이란?

정규 표현식, regexp 또는 regex라고 불리는 정규표현식(regular expression)은 일정한 규칙(패턴)을 가진 문자열을 표현하는 방법입니다. 복잡한 문자열 속에서 특정한 규칙으로 된 문자열을 검색한 뒤 추출하거나 바꿀 때 사용합니다. 또는, 문자열이 정해진 규칙에 맞는지 판단할 때도 사용합니다.

 

특정한 규칙을 가진 문자열의 집합을 추출할 수 있어서 주민등록 번호, 전화번호, 도서 ISBN 등 형식이 있는 문자열을 원본 문자열로부터 추출할 때 사용합니다. 다르게 말하면, Programming Language나 Text Editor 등에서 문자열의 검색과 치환을 위한 용도로 쓰이고 있습니다. 

  • 장점 : 일반적인 조건문으로는 복잡할 수 있지만, 정규 표현식을 이용하면 매우 간단하게 표현 할 수 있음.
  • 단점 : 코드가 간단한 만큼 가독성이 떨어져서 표현식을 숙지하지 않으면 이해하기 힘듬.

 

정규표현식 표현방법

정규표현식은 표준인 POSIX의 정규표현식과 POSIX 정규표현식에서 확장된 Perl방식의 PCRE가 대표적이고, 이외에도 수많은 정규표현식이 존재하며 정규 표현식 간에는 약간의 차이점이 있습니다.

정규 표현식에서 사용하는 기호를 Meta문자라고 하고 이 Meta문자는 표현식 내부에서 특정한 의미를 갖는 문자를 말하며, 공통적인 기본 Meta 문자의 종류는 아래와 같습니다.

 

공통 기본 Meta

정규 표현식 표현 설명
^x
문자열이 x로 시작
x$
문자열이 x로 끝
.x
임의의 한 문자를 표현(x가 마지막으로 끝남)
x+
x가 1번이상 반복
x?
x가 존재하거나 존재하지 않음.
x*
x가 0번이상 반복
x|y
x 또는 y를 찾음(or 연산자를 의미)
(x)
()안의 내용을 캡쳐하며, 그룹화
(x)(y)
그룹화 할 때, 자동으로 앞에서부터 1번부터 그룹 번호를 부여해서 캡쳐.
결과값에 그룹화한 Data가 배열 형식으로 그룹번호 순서대로 들어감.
(x)(?:y)
캡쳐하지 않는 그룹을 생성할 경우 ?:를 사용함.
결과값 배열에 캡쳐하지 않는 그룹은 들어가지 않음.
x{n}
x를 n번 반복한 문자를 찾음.
x{n,}
x를 n번이상 반복한 문자를 찾음.
x{n,m}
x를 n번이상 m번이하 반복한 문자를 찾음

 

한 문자만 지정하는 Meta 문자 : []

정규 표현식 표현 설명
[xy]
x, y 중 하나를 찾습니다.
[^xy]
x, y를 제외하고 문자 하나를 찾습니다.
(문자 클래스 내의 ^는 not을 의미)
[x-z]
x~z 사이의 문자 중 하나를 찾습니다.
\^
^(특수문자)를 식에 문자 자체로 포함합니다.(escape)
\b
문자와 공백 사이의 문자를 찾습니다.
\B
문자와 공백 사이가 아닌 값을 찾습니다.
\d
숫자를 찾습니다.
\D
숫자가 아닌 값을 찾습니다.
\s
공백문자를 찾습니다.
\S
공백이 아닌 문자를 찾습니다.
\t
Tab 문자를 찾습니다.
\v
Vertical Tab 문자를 찾습니다.
\w
알파벳 + 숫자 + _ 를 찾습니다.
\W
알파벳 + 숫자 + _ 을 제외한 모든 문자를 찾습니다.

 

 

자주 사용되는 패턴

1) 숫자만 : ^[0-9]*$

2) 영문자만 : ^[a-zA-Z]*$

3) 한글만 : ^[가-힣]*$

4) 영어 & 숫자만 : ^[a-zA-Z0-9]*$

5) E-Mail : ^[a-zA-Z0-9]+@[a-zA-Z0-9]+$

6) 휴대폰 : ^01(?:0|1|[6-9]) - (?:\d{3}|\d{4}) - \d{4}$

7) 일반전화 : ^\d{2.3} - \d{3,4} - \d{4}$

8) 주민등록번호 : \d{6} - [1-4]\d{6}

9) IP 주소 : ([0-9]{1,3}) . ([0-9]{1,3}) . ([0-9]{1,3}) . ([0-9]{1,3})

10) 라인 확인 : (?m)^[ \t]*\r?\n

 

정규식 공부하기 좋은 알고리즘 문제로 2021년 카카오 블라인드 테스트 1차 코딩테스트 1번 문제를 추천합니다.

 

코딩테스트 연습 - 신규 아이디 추천

카카오에 입사한 신입 개발자 네오는 카카오계정개발팀에 배치되어, 카카오 서비스에 가입하는 유저들의 아이디를 생성하는 업무를 담당하게 되었습니다. 네오에게 주어진 첫 업무는 새로 가

programmers.co.kr

 

 

 

위의 표현은 아래 사이트를 통해 나온 표현 방식입니다.

 

Regexper

 

regexper.com

참고 사이트

 

 

위키독스

온라인 책을 제작 공유하는 플랫폼 서비스

wikidocs.net

 

 

정규표현식(Regular Expression)을 소개합니다.

날이 갈수록 개인정보 보호에 관련하여 보안정책을 점진적으로 강화하고 있습니다. 이에 따라 Web에서 회원가입 시 Password 설정을 복잡해진 보안정책에 맞추다 보니 복잡하게 조합해야만 정상적

www.nextree.co.kr

 

글을 시작하며

이번 부스트캠프에서 처음으로 배운 개념입니다.

이전에는 단순히 for문에서 사용하지 않는 부분에서 _를 사용했는데 이런 부분을 알게 돼서 조금 더 자세히 공부하려고 합니다.

 

먼저 참고 자료로 아래 2개의 사이트를 참고했습니다. 더 자세히 확인하시고 싶으면 링크를 확인해주세요.

 

What is the meaning of single and double underscore before an object name?

Can someone please explain the exact meaning of having leading underscores before an object's name in Python, and the difference between both? Also, does that meaning stay the same whether the obj...

stackoverflow.com

 

 

파이썬에서 언더바/언더스코어(_) 의 의미와 역할

https://www.datacamp.com/community/tutorials/role-underscore-python Role of Underscore(_) in Python In this tutorial, you're going to learn about the uses of underscore(_) in python. www.datacamp.co..

eine.tistory.com

 

언더스코어(_)의 사용 용도로 4가지가 있습니다.

  1. 인터프리터에서 마지막 값 저장
  2. 무시하는 값
  3. 숫자값의 분리(자릿수 구분, 구분자)
  4. 변수나 함수명에 특별한 의미 또는 기능을 부여할 때

 

1. 인터프리터에서 마지막 값 저장

파이썬 인터프리터에서는 마지막 표현식의 결과값을 자동적으로 "_"라는 변수에 저장합니다.

 

 

2. 무시하는 값.

_는 무시하는 값으로도 쓰입니다. 해당 값을 unpack하기 싫으면, 해당 위치에 _를 넣으면 됩니다.

 

 

이는 for문에서도 사용할 수 있습니다.

 

 

3. 숫자값의 분리(자릿수 구분, 구분자)

 

숫자값이 길다면, 자릿수 구분을 위해 _를 중간에 넣어줄 수 있습니다.

 

 

4. 변수나 함수명에 특별한 의미 또는 기능을 부여할 때

 

변수, 함수, 클래스 명 등에 언더스코어(언더바)가 사용될 수 있습니다.

종류로는 4가지가 있습니다.

 

4-1. 앞에 하나의 언더스코어 _variable

 

앞에 하나의 언더스코어로 시작하는 이름은 내부 사용용도입니다.(internal use only)

 

위의 그림처럼 클래스내의 변수를 호출하면 접근이 가능합니다.

하지만 해당 모듈을 import 해서 사용하는 경우 다음과 같이 됩니다.

 

 

위에서 나오는 에러처럼 _Test2는 import가 안되는 것을 확인할 수 있습니다.

위와 같은 상황을 다르게 from underscore import * -> import underscore로 변경해보자

 

 

이처럼 _ 1개는 내부사용 전용이라는 뜻입니다.

 

4-2. 뒤의 하나의 언더스코어

 

가끔 파이썬 키워드에 해당하는 이름(예약어)을 변수명, 함수명, 클래스명으로 사용하고 싶은 경우 사용하면 됩니다.

 

 

위에서 보이는 것처럼 sum은 list, tuple의 값을 더하는 함수입니다.

sum을 변수로 사용한다면 꼬이게 되서 오류가 발생합니다.

이러한 상황을 피하기 위해 변수명을 sum 대신 sum_을 사용하면 됩니다.

 

 

4-3 앞의 두개의 언더스코어

 

앞에 두개의 언더바로 시작하는 방식으로 name mangling이라고도 한다. 

아래를 통해 확인해보자

 

 

dir 함수를 통해 보면 obj안에 함수와 변수에 __list가 없는 것을 확인할 수 있다. 이처럼 언더스코어 2개로 시작하는 것은 pivate access modifier(접근 지정자)의 역할을 한다. 변수뿐만 아니라 메소드에서도 사용 가능하다.

 

그러면 어떻게 접근하는지 확인해보자.

 

 

mangling된 변수에 접근하려면 위와 같이 함수를 사용하여 접근을 해야한다.

 

추가적으로 mangling된 변수에 값을 직접 추가하는 방식은 property 데코레이터를 사용하면 가능하다.

 

 

4-4 앞뒤로 2개의 언더스코어

이것은 특수한 예약 함수나 변수, 그리고 함수명으로 매직 메소드(magic method) 또는 dunder 메소드라고 불립니다.

대표적으로 __init__, __add__, __len__, __main__ 등이 있다.

참고 자료는 아래 링크에서 확인하면 됩니다.

 

 

Dunder or magic methods in Python - GeeksforGeeks

A Computer Science portal for geeks. It contains well written, well thought and well explained computer science and programming articles, quizzes and practice/competitive programming/company interview Questions.

www.geeksforgeeks.org

 

+ Recent posts