User Tools

Site Tools


why_n-1_gradient_explanation

Differences

This shows you the differences between two versions of the page.

Link to this comparison view

Both sides previous revisionPrevious revision
Next revision
Previous revision
why_n-1_gradient_explanation [2025/09/04 12:15] hkimscilwhy_n-1_gradient_explanation [2025/09/05 19:51] (current) – [리소스를 많이 사용하지 않고 msr값이 최소가 되는 v값을 찾는 방법] hkimscil
Line 1: Line 1:
 +====== mean X를 중심으로 x값들을 구해서 (x-v)에 사용하는 경우 ======
 +
 <code> <code>
 #library(ggplot2) #library(ggplot2)
Line 25: Line 27:
 hist(x) hist(x)
  
-x.span <- seq(from = min(x),  +x.span <- seq(from = mean(x)-3*sd(x),  
-              to = max(x),  +              to = mean(x)+3*sd(x),  
-              by = 1)+              by = .1)
  
 residuals <- function(x, v) { residuals <- function(x, v) {
Line 60: Line 62:
 # 값으로 샘플의 평균을 사용했을 때의 # 값으로 샘플의 평균을 사용했을 때의
 # residual 값이다.  # residual 값이다. 
 +# x.span은 샘플의 평균을 중심으로 
 +# 여러가지 값을 사용하는 것을 
 +# 가정한다.
 +
 +
  
 for (i in x.span) { for (i in x.span) {
   res.x <- residuals(x,i)   res.x <- residuals(x,i)
-  srs.x <- sum(res.x)  +#  srs.x <- sum(res.x)  
   ssr.x <- ssr(x,i)   ssr.x <- ssr(x,i)
   msr.x <- msr(x,i)   msr.x <- msr(x,i)
-  srs <- append(srs, srs.x)+#  srs <- append(srs, srs.x)
   ssrs <- append(ssrs, ssr.x)   ssrs <- append(ssrs, ssr.x)
   msrs <- append(msrs, msr.x)   msrs <- append(msrs, msr.x)
   vs <- append(vs, i)   vs <- append(vs, i)
 } }
 +# 아래 plot은 SS값들이나 (두번째는)
 +# MS값들을 v값이 변화함에 따라서
 +# (x.span의 범위에 따라서 변화)
 +# 어떻게 변화하는지 구한 것
 plot(ssrs) plot(ssrs)
 plot(msrs) plot(msrs)
-plot(srs) 
  
 +
 +# 아래는 위에서 계산한 msr 값들을 저장한
 +# msrs값들 중에서 최소값이 되는 것을 찾은 
 +# 것. 우리는 이것이 샘플의 평균임을 안다. 
 min(msrs) min(msrs)
 +# 최소값일 때의 위치 (msrs에서 몇번째인지)
 min.pos.msrs <- which(msrs == min(msrs)) min.pos.msrs <- which(msrs == min(msrs))
 min.pos.msrs min.pos.msrs
 +# 그 위치에 해당하는 (그 때 사용된) v값
 print(vs[min.pos.msrs]) print(vs[min.pos.msrs])
-mean(x) +</code>
-plot(vs, msrs) +
-plot(vs, ssrs)+
  
 +다시 설명하면 위의 코드는 [sum(x-mean(x)^2 / n]을 (= ms값 혹은 분산값임) 구하는 식에 mean(x)대신에 다양한 x값을 넣어 본 것이다. 그리고, 이 때 ms값 중에서 최소값이 되는 지점을 찾아서 이 때 사용된 v값을 (mean(x)대신에 사용된) 알아 본것이다. 이 v값이 mean(x)이 되는 것을 확인하여 mean(x)값으로 빼서 구한 SS값이 가장 작은 ms값을 (혹은 SS값을) 갖는다는 것을 보여준다.
 +
 +
 +====== 리소스를 많이 사용하지 않고 msr값이 최소가 되는 v값을 찾는 방법 ======
 +
 +위 방법의 단점은 x.span의 값을 길게 나열하여 한번씩 넣어서 msr값을 구하여 최소값을 보는데 리소스를 너무 사용한다는 것이다.
 +아래는 그 단점을 극복하는 방법이다. 
 +<WRAP group>
 +<WRAP half column>
 +<code>
 # the above no gradient # the above no gradient
-# mse 값으로 계산 rather than sse  
-# 후자는 값이 너무 커짐 
  
 gradient <- function(x, v){ gradient <- function(x, v){
   residuals = x - v   residuals = x - v
-  # y = (x-v)^2 +  # y = (sum(x-v)^2)/n 혹은 (mean(x-v)^2)  
-  # dy/dv = 2(x-v)*-1 chain rule +  # 의 식이 ms값을 구하는 식인데  
-  # dy/dv = -2(x-v)+  # 이를 v에 대해서 미분하면 chain rule을 써야 한다 
 +  # 자세한 것은 http://commres.net/wiki/estimated_standard_deviation 
 +  # 문서 중에 미분 부분 참조 
 +  # dy/dv = 2(x-v)*-1 ) / n chain rule 
 +  # dy/dv = -2 (x-v) / n = -2 (mean(residual)
   dx = -2 * mean(residuals)   dx = -2 * mean(residuals)
-  return(list("ds" = dx))+  return(list("ds" = dx)
 +  return(dx)
 } # function returns ds value } # function returns ds value
  
 +
 +
 +
 +
 +
 +
 +
 +
 +
 +
 +
 +
 +>
 +</code>
 +</WRAP>
 +<WRAP half column>
 +이후 일련의 코드의 목적은 v값이 최소값이 되는 지점을 자동적으로 찾아보려는 것이다. 이것을 위해서 우선 v값으로 사용할 첫 점수를 랜덤하게 구한 후 (아래 그래프에서 빨간색 지점), 자동적으로 그 다음 v 점수를 찾고 (녹색지점), 그 다음 v 점수를 찾고 (황금색 지점), . . . 이런 과정을 계속하면서 각 v 점수에서의 msr값을 구해서 이에 해당하는 v값을 찾아 보려고 한다. 빨간색, 녹색, 황금색, . . . 이를 자동적으로 구하기 위해서 두가지 방법을 사용하는데 그 것이
 +  * gradient function과
 +  * learning_rate 값이다. 
 +gradient 펑션은 dy/dv 의 연쇄 미분식인 ([[:chain rules]]) -2(x-v) / n = -2 mean(res) 값을 구하는 것이다. 이렇게 구한 값에 learning_rate값을 곱한후, 이것을 먼저 사용한 v값에서 (빨간색 지점) 빼 주어 다음 v값으로 (녹색지점) 사용하려고 한다. 이 녹색지점에서의 v값을 사용했을 때의 gradient값을 구한 후 다시 이값에 learning_rate인 0.1을 곱하여 그 다음 v값을 구하여 사용한다. 이렇게 구하는 v값들은 0.1씩 곱해주는 효과때문에 오른 쪽으로 옮겨가는 지점이 "<fc #ff0000>**점진적으로 줄어들게 되고**</fc>" 이 지점이 msr의 최소값이 되는 지점으로 가게 된다. 
 +
 +
 +{{:pasted:20250905-190437.png}}
 +
 +</WRAP>
 +</WRAP>
 +
 +
 +<WRAP group>
 +<WRAP half column>
 +<code>
 residuals <- function(x, v) { residuals <- function(x, v) {
   return(x - v)   return(x - v)
Line 110: Line 168:
 #  return(mean(residuals^2)) #  return(mean(residuals^2))
 } }
 +</code>
 +</WRAP>
 +<WRAP half column>
 +msr값을 구하기 위한 function 
  
 +</WRAP>
 +</WRAP>
 +
 +<WRAP group>
 +<WRAP half column>
 +<code>
 +zx <- (x-mean(x))/sd(x)
 # pick one random v in (x-v) # pick one random v in (x-v)
 v <- rnorm(1) v <- rnorm(1)
 +
 +
 +
 +
 +
 +
 +
 +
 +
 +>
 +</code>
 +</WRAP>
 +<WRAP half column>
 +comment
 +  * 랜덤하게 v값을 찾음 ''v <- rnorm(1)'' 
 +  * 원래는 mean(x)값 근처의 값을 랜덤하게 골라야 하므로
 +  * ''v <- rnorm(1, mean(x), sd(x))'' 와 같이 써야 하지만 (현재의 경우, '' rnorm(1, 50, 5) ''가 된다) 
 +  * 그렇게 하질 않고 x 집합의 원소들을 표준점수화 한 후 '' zx <- (x-mean(x))/sd(x) ''
 +  * (이렇게 표준점수화 하면 x 변인의 평균이 0, 표준편차가 1 이 되는 집합으로 변한다)
 +  * '' v <- rnorm(1, 0, 1) ''로 구한다. 뒤의 인자인 0, 1 은 default이모로 생략.
 +  * 이렇게 하는 이유는 혹시 나중에 다른 x집합에 똑같은 작업을 하더라도 그 집합의 평균과 표준편차를 사용하지 않고
 +  * 단순히 '' rnorm(1)'' 을 이용해서 찾으려고 하는 것이다. 
 +
 +</WRAP>
 +</WRAP>
 +
 +
 +<WRAP group>
 +<WRAP half column>
 +<code>
 # Train the model with scaled features # Train the model with scaled features
 learning.rate = 1e-1 learning.rate = 1e-1
 +</code>
 +</WRAP>
 +<WRAP half column>
 +comment
 +  * 이 0.1은 gradient function으로 구한 해단 v값에 대한 y 기울기 값을 (미분값)
 +  * 구한 후, 여기에 곱하기 위해서 지정한다.
 +</WRAP>
 +</WRAP>
  
-grads <- c() +<WRAP group> 
-ssrs <- c()+<WRAP half column> 
 + 
 +<code>
 msrs <- c() msrs <- c()
-mres <- c() 
 vs <- c() vs <- c()
-steps <- c() 
-# Record Loss for each epoch: 
-zx <- (x-mean(x))/sd(x) 
  
 nlen <- 75 nlen <- 75
 for (epoch in 1:nlen) { for (epoch in 1:nlen) {
   residual <- residuals(zx, v)   residual <- residuals(zx, v)
-  # ssr.x <- ssr(zx, v) +  msr.x <- msr(zx, v)
-  # msr.x <- msr(zx, v+
-  # ssrs <- append(ssrs, ssr.x) +
-  # msrs <- append(msrs, msr.x)+
      
   grad <- gradient(zx, v)   grad <- gradient(zx, v)
-  # grads <- append(grads, grad$ds) +  step.v <- grad * learning.rate #  
-  step.v <- grad$ds * learning.rate +  v <- v - step.v # 그 다음 v값 
-  steps <- append(steps, step.v) +  vs <- append(vs, v) # v값 저장
-  v <- v - step.v +
-  vs <- append(vs, v)+
 } }
  
-tail(grads) 
-tail(srs) 
 tail(msrs) tail(msrs)
-tail(ssrs) 
 tail(vs) tail(vs)
  
-plot(srs) 
 plot(msrs) plot(msrs)
-plot(ssrs) 
 plot(vs) plot(vs)
-plot(grads)+</code> 
 +</WRAP> 
 +<WRAP half column> 
 +comment 
 +</WRAP> 
 +</WRAP> 
 + 
 +<WRAP group> 
 +<WRAP half column> 
 +<code>
 # scaled # scaled
-+vs 하는 값들의 집합 
-zx <- (x-mean(x))/sd(x) +
-# v.표준화 <- (v.원래 - mean(x))/sd(x) +
-v.orig <- (v*sd(x))+mean(x)  +
-v.orig +
- +
-steps +
 vs.orig <- (vs*sd(x))+mean(x)  vs.orig <- (vs*sd(x))+mean(x) 
 vs.orig vs.orig
-grads 
- 
  
 +# 마지막 v값이 최소값에 근접한 값
 +
 +v.orig <- (v*sd(x))+mean(x) 
 +v.orig
 </code> </code>
 +</WRAP>
 +<WRAP half column>
 +comment
 +</WRAP>
 +</WRAP>
why_n-1_gradient_explanation.1756955759.txt.gz · Last modified: 2025/09/04 12:15 by hkimscil

Donate Powered by PHP Valid HTML5 Valid CSS Driven by DokuWiki