Skip to content

Latest commit

 

History

History
604 lines (495 loc) · 21.1 KB

220516.md

File metadata and controls

604 lines (495 loc) · 21.1 KB

워드 클라우드

  • 텍스트 데이터를 분석하는 대표적인 방법
  • 대상 데이터에서 단어를 추출하고 단어들의 출현 빈도수를 계산하여 시각화하는 기능을 함
  • JRE 필요
  • 텍스트 파일은 마지막에 줄바꿈 후 저장해야 함
  • UTF-로 저장

명사 추출

필요 패키지

  • wordcloud
  • RcppMeCab (KoNLP에서 대체)
  • RColorBrewer
library(wordcloud)
library(RColorBrewer)
library(RmecabKo)

text <- readLines("mis_document.txt",encoding="UTF-8")  # 파일 읽기

pal2 <- brewer.pal(8, "Dark2")                          # 팔레트 생성
noun <- sapply(text, nouns, USE.NAMES=F)                # 명사 추출
print(noun)
> noun <- sapply(text, nouns, USE.NAMES=F)
> noun
$`1. (여성가족부) 불법촬영 등 디지털 성범죄로부터 안전한 사회를 만들기 위해 국민들께 드리는 말씀`
 [1] "여성"   "가족"   "부"     "불법"   "촬영"   "등"     "디지털" "성범죄" "안전"   "사회"  
[11] "국민"   "말씀"  

[[2]]
NULL

$`존경하는 국민 여러분!`
[1] "존경"   "국민"   "여러분"

$...
 [1] "여성"   "가족"   "부"     "장관"   "정현백" "우리"   "사회"   "들불"   "미투"   "운동"  
[11] "계기"   "일상"   "폭력"   "차별"   "여성"   "외침"   "연대"   "이"     "성"     "평등"  
[21] "세상"   "우리"   "사회"   "무엇"   "추동"   "일상"   "성"     "평등"   "뿌리"   "문제"  
[31] "우리"   "앞"     "불법"   "촬영"   "촬영"   "물"     "유포"   "포함"   "디지털" "성범죄"

[[5]]
NULL

$...
 [1] "디지털" "성범죄" "피해"   "고통"   "분"     "나"     "자신"   "범죄"   "대상"   "불안감"
[11] "호소"   "국민"   "앞"     "저"     "마음"   "순간"   "여성"   "몸"     "상품"   "불법"  
[21] "영상물" "광범위" "소비"   "이"     "누군가" "경제"   "이득"   "저"     "자리"   "정부"  
[31] "대표"   "정부"   "디지털" "성범죄" "피해"   "현안"   "중대"   "인식"   "각오"   "정책"  
[41] "추진"   "말씀"  
...

위와 같이 명사를 추출해낸 것을 확인할 수 있다.

빈도수 높은 단어를 막대그래프로 작성

noun2 <- unlist(noun)                                # 추출된 명사 통합
wordcount <- table(noun2)                            # 단어 빈도수 계산
temp <- sort(wordcount, decreasing=T)[1:10]          # 상위 10개 추출
temp
barplot(temp, 
        names.arg=names(temp),                       # 막대 이름을 단어로 표시시
        col = "lightblue",
        main="빈도수 높은 단어", ylab="단어 빈도수")
> temp
noun2
  불법     등   여성   수사   촬영 디지털 성범죄   유포 경찰청 카메라 
    29     27     24     23     22     12     11     11     10     10 

Rplot18

추가

  • 여기서는 명사에 공백같은 의미 없는 것이 잡히지 않았지만 만약 잡혔다면 제거하고 그래프를 그려야 함

워드 클라우드 작성

wordcloud(names(wordcount), # 단어들
          freq=wordcount,   # 단어들의 빈도
          scale=c(6,0.7),   # 단어의 폰트 크기 (최대, 최소)
          min.freq=3,       # 단어의 최소 빈도수
          random.order=F,   # 단어의 출력 위치, F는 빈도수가 높을 수록 중앙
          rot.per=.1,       # 90도 회전 단어 비율
          colors=pal2)      # 단어의 색색

Rplot19

워드클라우드 수정

  • '수', '앞', '저', '등'과 같이 의미 없는 단어들도 포함되어 있음
  • 중요한 단어이지만 사전에 없어서 생략된 단어도 있을 수 있음
noun <- sapply(text, nouns, USE.NAMES=F)
noun2 <- unlist(noun)

# 무의미한 단어 제거
noun2 <- noun2[nchar(noun2)>1] # 1글자 단어 제거
noun2 <- gsub("경우","",noun2) # '경우' 제거
noun2 <- gsub("하지","",noun2) # '하지' 제거
noun2 <- gsub("때문","",noun2) # '때문' 제거거

wordcount <- table(noun2)
wordcloud(names(wordcount),
          freq=wordcount,
          scale=c(6,0.7),
          min.freq=3,
          random.order=F,
          rot.per=.1,
          colors=pal2)

Rplot20

회귀분석 용어

  • 독립변수 (설명변수)
  • 종속변수 (반응변수)
  • 예측모델
    • 독립변수와 종속변수에 해당하는 자료를 모아 관계를 분석하고 예측에 사용할 수 있는 통계적 방법으로 정리한 것
  • 회귀분석
    • 회귀 이론을 기초로 독립변수가 종속변수에 미치는 영향을 파악하여 예측모델을 도출하는 통계적 방법
  • 회귀식
    • 회귀모델에서 독립변수와 종속변수 사이의 관계를 수학식 형태로 표현한 것
  • 단순 회귀
    • 독립변수의 수가 하나인 경우
  • 다중 회귀
    • 독립 변수의 수가 두 개 이상인 경우

단순선형 회귀분석의 목표

단순선형 회귀

  • 독립변수(x)와 종속변수(y) 사이의 선형 관계를 파악하고 이를 예측에 활용하는 통계적 방법
  • 단순선형 회귀식은 1차식의 형태를 가짐

y = Wx + b (W, b는 상수)

목표

  • 위 식에서 상수인 W와 b를 찾는 것

주행속도와 제동거리 사이의 회귀모델

head(cars)
plot(dist~speed, data=cars)   # 산점도를 통한 선형 관계 확인

model <- lm(dist~speed, cars) # 회귀모델 구하기
model

abline(model)                 # 회귀선을 산점도 위에 표시
coef(model)[1]                # b 값 출력
coef(model)[2]                # W 값 출력
> head(cars)
  speed dist
1     4    2
2     4   10
3     7    4
4     7   22
5     8   16
6     9   10

> model <- lm(dist~speed, cars) # 회귀모델 구하기

> model

Call:
lm(formula = dist ~ speed, data = cars)

Coefficients:
(Intercept)        speed  
    -17.579        3.932  

> coef(model)[1]                # b 값 출력
(Intercept) 
  -17.57909 

> coef(model)[2]                # W 값 출력
   speed 
3.932409 

Rplot21

회귀식

dist = 3.932 * speed - 17.579

주행속도에 따른 제동거리 계산

b <- coef(model)[1]
W <- coef(model)[2]

speed <- 30
dist <- W*speed + b
dist

speed <- 35
dist <- W*speed + b
dist

speed <- 40
dist <- W*speed + b
dist
> b <- coef(model)[1]

> W <- coef(model)[2]

> speed <- 30

> dist <- W*speed + b

> dist
   speed 
100.3932 

> speed <- 35

> dist <- W*speed + b

> dist
   speed 
120.0552 

> speed <- 40

> dist <- W*speed + b

> dist
   speed 
139.7173 

추가

  • 단순선형 회귀모델을 예측에 활용할 때 예측한 값이 실제값과 오차가 있을 수 있다는 것을 인지해야 함

예상 제동거리, 실제 제동거리, 오차 구하기

speed <- cars[,1]
pred <- W*speed + b
pred
compare <- data.frame(pred, cars[,2],pred-cars[,2])
colnames(compare) <- c('예상','실제','오차')
head(compare)
> speed <- cars[,1]

> pred <- W*speed + b

> pred
 [1] -1.849460 -1.849460  9.947766  9.947766 13.880175 17.812584 21.744993 21.744993 21.744993 25.677401
[11] 25.677401 29.609810 29.609810 29.609810 29.609810 33.542219 33.542219 33.542219 33.542219 37.474628
[21] 37.474628 37.474628 37.474628 41.407036 41.407036 41.407036 45.339445 45.339445 49.271854 49.271854
[31] 49.271854 53.204263 53.204263 53.204263 53.204263 57.136672 57.136672 57.136672 61.069080 61.069080
[41] 61.069080 61.069080 61.069080 68.933898 72.866307 76.798715 76.798715 76.798715 76.798715 80.731124

> compare <- data.frame(pred, cars[,2],pred-cars[,2])

> colnames(compare) <- c('예상','실제','오차')

> head(compare)
       예상 실제       오차
1 -1.849460    2  -3.849460
2 -1.849460   10 -11.849460
3  9.947766    4   5.947766
4  9.947766   22 -12.052234
5 13.880175   16  -2.119825
6 17.812584   10   7.812584

다중선형 회귀모델 만들기

예시

  • 키와 몸무게를 이용해 혈당 수치를 예측하는 문제
  • 키와 몸무게가 독립변수 x1, x2
  • 혈당 수치가 종속변수 y

독립변수가 n개인 다중선형 회귀모델

y = β0 + β1x1 + β2x2 + ... + βnxn

library(car)
head(Prestige)

newdata <- Prestige[,c(1:4)]             # 회귀식 작성을 위한 데이터 준비
plot(newdata, pch=16, col="blue",        # 산점도를 통해 변수 간 관계 확인
     main="Matrix Scatterplot")

mod1 <- lm(income~education + prestige + # 회귀식 도출
             women, data=newdata)
summary(mod1)
> library(car)

> head(Prestige)
                    education income women prestige census type
gov.administrators      13.11  12351 11.16     68.8   1113 prof
general.managers        12.26  25879  4.02     69.1   1130 prof
accountants             12.77   9271 15.70     63.4   1171 prof
purchasing.officers     11.42   8865  9.11     56.8   1175 prof
chemists                14.62   8403 11.68     73.5   2111 prof
physicists              15.64  11030  5.13     77.6   2113 prof

> newdata <- Prestige[,c(1:4)]             # 회귀식 작성을 위한 데이터 준비

> plot(newdata, pch=16, col="blue",        # 산점도를 통해 변수 간 관계 확인
+      main="Matrix Scatterplot")

> mod1 <- lm(income~education + prestige + # 회귀식 도출
+              women, data=newdata)

> summary(mod1)

Call:
lm(formula = income ~ education + prestige + women, data = newdata)

Residuals:
    Min      1Q  Median      3Q     Max 
-7715.3  -929.7  -231.2   689.7 14391.8 

Coefficients:
            Estimate Std. Error t value Pr(>|t|)    
(Intercept) -253.850   1086.157  -0.234    0.816    
education    177.199    187.632   0.944    0.347    
prestige     141.435     29.910   4.729 7.58e-06 ***
women        -50.896      8.556  -5.948 4.19e-08 ***
---
Signif. codes:  0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1

Residual standard error: 2575 on 98 degrees of freedom
Multiple R-squared:  0.6432,	Adjusted R-squared:  0.6323 
F-statistic: 58.89 on 3 and 98 DF,  p-value: < 2.2e-16

Rplot22

Prestige 데이터셋

  • 행의 이름은 직군
  • 열의 이름
    • education: 교육연수(독립변수)
    • income: 연봉(종속변수)
    • women: 여성의 비율(독립변수)
    • prestige: 직군에 대한 평판도(독립변수)

산점도 분석

  • education과 prestige는 income과 양의 상관 관계를 보임
  • women은 income과 음의 상관 관계를 보임

lm()

  • ~앞이 종속변수, 뒤가 독립변수
  • 독립변수가 여러 개면 +로 연결

회귀모델

income = (-253.850)+(177.199*education)+(141.435*prestige)-(50.896*women)

summary()

  • Pr(>|t|) 옆의 '*'는 해당 변수가 종속변수를 설명하는 데 얼마나 중요한 변수인가를 나타냄, 많을수록 통계적으로 중요하다는 의미
  • p-value(유의수준) 값은 구한 회귀모델이 의미 있는 모델인지, 혹은 신뢰할 수 있는 모델인지를 나타냄, 작을수록 의미 있는 모델
  • Adjusted R-squared 값은 모델의 설명력을 나타냄, 0~1 사이의 값을 갖고 클수록 회귀모델이 현실을 잘 설명할 수 있다는 의미

다중선형 회귀모델에서 변수의 선택

  • 모든 독립변수가 종속변수를 설명하는 데 동일하게 기여하는 것은 아님
library(MASS)
newdata2 <- Prestige[,c(1:5)]
head(newdata2)
mod2 <- lm(income~education + prestige + women + census, data=newdata2)
mod3 <- stepAIC(mod2) # 변수 선택 진행
mod3                  # 변수 선택 후 결과 확인
summary(mod3)         # 회귀모델 상세 내용 확인인
> head(newdata2)
                    education income women prestige census
gov.administrators      13.11  12351 11.16     68.8   1113
general.managers        12.26  25879  4.02     69.1   1130
accountants             12.77   9271 15.70     63.4   1171
purchasing.officers     11.42   8865  9.11     56.8   1175
chemists                14.62   8403 11.68     73.5   2111
physicists              15.64  11030  5.13     77.6   2113

> mod3 <- stepAIC(mod2) # 변수 선택 진행
Start:  AIC=1607.93
income ~ education + prestige + women + census

            Df Sum of Sq       RSS    AIC
- census     1    639658 649654265 1606.0
- education  1   5558323 654572930 1606.8
<none>                   649014607 1607.9
- prestige   1 143207106 792221712 1626.3
- women      1 212639294 861653901 1634.8

Step:  AIC=1606.03
income ~ education + prestige + women

            Df Sum of Sq       RSS    AIC
- education  1   5912400 655566665 1605.0
<none>                   649654265 1606.0
- prestige   1 148234959 797889223 1625.0
- women      1 234562232 884216497 1635.5

Step:  AIC=1604.96
income ~ prestige + women

           Df Sum of Sq        RSS    AIC
<none>                   655566665 1605.0
- women     1 234647032  890213697 1634.2
- prestige  1 811037947 1466604612 1685.1

> mod3                  # 변수 선택 후 결과 확인

Call:
lm(formula = income ~ prestige + women, data = newdata2)

Coefficients:
(Intercept)     prestige        women  
     431.57       165.87       -48.38  


> summary(mod3)         # 회귀모델 상세 내용 확인인

Call:
lm(formula = income ~ prestige + women, data = newdata2)

Residuals:
    Min      1Q  Median      3Q     Max 
-7620.9 -1008.7  -240.4   873.1 14180.0 

Coefficients:
            Estimate Std. Error t value Pr(>|t|)    
(Intercept)  431.574    807.630   0.534    0.594    
prestige     165.875     14.988  11.067  < 2e-16 ***
women        -48.385      8.128  -5.953 4.02e-08 ***
---
Signif. codes:  0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1

Residual standard error: 2573 on 99 degrees of freedom
Multiple R-squared:   0.64,	Adjusted R-squared:  0.6327 
F-statistic: 87.98 on 2 and 99 DF,  p-value: < 2.2e-16

추가

  • lm()에서 income~education + prestige + women + censusincome~.으로 줄일 수 있는데 이때 '.'은 income을 제외한 나머지가 모두 독립변수라는 의미
  • stepAIC()는 매개변수로 받은 모델에서 불필요한 변수를 제거해 나가는 방식으로 작업
  • 그에 따라 마지막에는 prestige와 women만이 남은 것을 확인할 수 있음
  • 회귀식은 income = 431.57 + (165.87*prestige) - (48.38*women)
  • Adjusted R-squared 값이 mod3는 변수 2개에 0.6327, 앞의 mod1은 변수 3개에 0.6323으로 설명력은 거의 동일하지만 mod3가 더 단순하기 때문에 mod3가 더 나은 모델

Logistic regression의 개념

Logistic regression

  • 로지스틱 회귀
  • 회귀모델에서 종속변수의 값의 형태가 연속형 숫자가 아닌 범주형 값인 경우를 다루기 위해서 만들어진 통계적 방법

분류

  • 주어진 데이터로부터 어떤 범주를 예측하는 분야

로지스틱 회귀모델 만들기

  • 로지스틱 회귀도 기본적으로 회귀 기법이기 때문에 종속변수가 숫자로 표현되어야 함
iris.new <- iris
iris.new$Species <- as.integer(iris.new$Species) # 범주형 자료를 정수로 변환
head(iris.new)
mod.iris <- glm(Species~., data=iris.new)        # 로지스틱 회귀모델 도출
summary(mod.iris)
> head(iris.new)
  Sepal.Length Sepal.Width Petal.Length Petal.Width Species
1          5.1         3.5          1.4         0.2       1
2          4.9         3.0          1.4         0.2       1
3          4.7         3.2          1.3         0.2       1
4          4.6         3.1          1.5         0.2       1
5          5.0         3.6          1.4         0.2       1
6          5.4         3.9          1.7         0.4       1

> mod.iris <- glm(Species~., data=iris.new)        # 로지스틱 회귀모델 도출

> summary(mod.iris)

Call:
glm(formula = Species ~ ., data = iris.new)

Deviance Residuals: 
     Min        1Q    Median        3Q       Max  
-0.59215  -0.15368   0.01268   0.11089   0.55077  

Coefficients:
             Estimate Std. Error t value Pr(>|t|)    
(Intercept)   1.18650    0.20484   5.792 4.15e-08 ***
Sepal.Length -0.11191    0.05765  -1.941   0.0542 .  
Sepal.Width  -0.04008    0.05969  -0.671   0.5030    
Petal.Length  0.22865    0.05685   4.022 9.26e-05 ***
Petal.Width   0.60925    0.09446   6.450 1.56e-09 ***
---
Signif. codes:  0 ‘***’ 0.001 ‘**’ 0.01 ‘*’ 0.05 ‘.’ 0.1 ‘ ’ 1

(Dispersion parameter for gaussian family taken to be 0.04800419)

    Null deviance: 100.0000  on 149  degrees of freedom
Residual deviance:   6.9606  on 145  degrees of freedom
AIC: -22.874

Number of Fisher Scoring iterations: 2

로지스틱 회귀모델을 이용한 예측

# 예측 대상 데이터 생성(데이터프레임)
unknown <- data.frame(rbind(c(5.1, 3.5, 1.4, 0.2)))
names(unknown) <- names(iris)[1:4]
unknown

pred <- predict(mod.iris, unknown) # 품종 예측
pred
round(pred, 0)

# 실제 품종명 알아보기
pred <- round(pred, 0)
pred
levels(iris$Species)
levels(iris$Species)[pred]
> # 예측 대상 데이터 생성(데이터프레임)
> unknown <- data.frame(rbind(c(5.1, 3.5, 1.4, 0.2)))

> names(unknown) <- names(iris)[1:4]

> unknown
  Sepal.Length Sepal.Width Petal.Length Petal.Width
1          5.1         3.5          1.4         0.2

> pred <- predict(mod.iris, unknown) # 품종 예측

> pred
        1 
0.9174506 

> round(pred, 0)
1 
1 

> # 실제 품종명 알아보기
> pred <- round(pred, 0)

> pred
1 
1 

> levels(iris$Species)
[1] "setosa"     "versicolor" "virginica" 

> levels(iris$Species)[pred]
[1] "setosa"

다수의 데이터에 대한 예측

test <- iris[,1:4]
pred <- predict(mod.iris, test)    # 모델을 이용한 예측
pred <- round(pred, 0)
pred
answer <- as.integer(iris$Species) # 실제 품종 정보
pred == answer                     # 예측 품종과 실제 품종이 같은지 비교
acc <- mean(pred == answer)        # 예측 정확도 계산
acc
> pred
  1   2   3   4   5   6   7   8   9  10  11  12  13  14  15  16  17  18  19  20  21  22  23  24  25  26  27 
  1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1 
 28  29  30  31  32  33  34  35  36  37  38  39  40  41  42  43  44  45  46  47  48  49  50  51  52  53  54 
  1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   1   2   2   2   2 
 55  56  57  58  59  60  61  62  63  64  65  66  67  68  69  70  71  72  73  74  75  76  77  78  79  80  81 
  2   2   2   2   2   2   2   2   2   2   2   2   2   2   2   2   3   2   2   2   2   2   2   2   2   2   2 
 82  83  84  85  86  87  88  89  90  91  92  93  94  95  96  97  98  99 100 101 102 103 104 105 106 107 108 
  2   2   3   2   2   2   2   2   2   2   2   2   2   2   2   2   2   2   2   3   3   3   3   3   3   3   3 
109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 
  3   3   3   3   3   3   3   3   3   3   3   2   3   3   3   3   3   3   3   3   3   3   3   3   3   2   3 
136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 
  3   3   3   3   3   3   3   3   3   3   3   3   3   3   3 

> answer <- as.integer(iris$Species) # 실제 품종 정보

> pred == answer                     # 예측 품종과 실제 품종이 같은지 비교
    1     2     3     4     5     6     7     8     9    10    11    12    13    14    15    16    17    18 
 TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE 
   19    20    21    22    23    24    25    26    27    28    29    30    31    32    33    34    35    36 
 TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE 
   37    38    39    40    41    42    43    44    45    46    47    48    49    50    51    52    53    54 
 TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE 
   55    56    57    58    59    60    61    62    63    64    65    66    67    68    69    70    71    72 
 TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE FALSE  TRUE 
   73    74    75    76    77    78    79    80    81    82    83    84    85    86    87    88    89    90 
 TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE FALSE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE 
   91    92    93    94    95    96    97    98    99   100   101   102   103   104   105   106   107   108 
 TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE 
  109   110   111   112   113   114   115   116   117   118   119   120   121   122   123   124   125   126 
 TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE FALSE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE 
  127   128   129   130   131   132   133   134   135   136   137   138   139   140   141   142   143   144 
 TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE FALSE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE  TRUE 
  145   146   147   148   149   150 
 TRUE  TRUE  TRUE  TRUE  TRUE  TRUE 

> acc <- mean(pred == answer)        # 예측 정확도 계산

> acc
[1] 0.9733333