보스턴주택가격예측
1. 문제정의
🔶보스턴주택가격 데이터를 사용하여 집값을 예측하는 실습진행
🔶회귀모델 사용하기
🔶 LinearRegression , SGDRegression
2. 데이터수집
boston_housing.csv 파일 사용
📌fetch_openml : 사이킷런에서 제공하는 데이터셋 관련도구, DataFrame으로 변환하여 가져오는방법
컬럼설명
- CRIM : 지역별 범죄 발생률
- ZN :25,000평방피트를 초과하는 거주지역 비율
- INDUS : 비상업지역 넓이 비율
- CHAS : 찰스강에 대한 더미변수 (1: 강의경계 , 0 그외)
- NOX : 일산화 질소 농도
- RM : 거주할수 있는 방의 갯수
- AGE : 1940년 이전에 건축된 소유 주택의 비율
- DIS : 5개 주요 고용 센터까지의 가중거리
- RAD
- 고속도로 접근 용이도
- TAX
- 10,000달러당 재산세율
- PTRATIO
- 지역의 교사와 학생비율
- B
- 지역의 흑인 거주 비율
- LSTAT :
- 하위계층의 비율
- MEDV
- 본인소유의 주택가격 (중앙값)
기술통계량 확인
![[Screenshot_276.png]]
--> 보아하니 수치가 들쭉날쭉 하기 때문에 스케일링이 필요
3. 전처리
Data Scaling
단위가 다 다를 경우에는 특성이 모델에 미치는 영향이 서로 달라지기때문에 사용
🔶Standard Scaler
- 평균값에 얼마나 분산이 되어있는지를 단위로 변환하는 방법
- 평균은 0. 분산은 1인 스케일로 변환
- 즉 평균에 얼마나 멀리 떨어져있는가로 해서 판단
🔰주의! : 전처리 끝나고 하는것임
4. EDA
학습용으로 정제된 데이터라서 이번에는 생략
5. 모델링
# 선형회귀모델
linear_model = LinearRegression()
# 경사하강모델
sgd_model = SGDRegressor(eta0=4e-2,max_iter=5000,verbose=0,random_state=SEED)
6. 훈련
선형회귀모델
linear_model.fit(X_train,y_train)
r2_score = linear_model.score(X_test,y_test)
print(f'r2 score : {r2_score*100:.2f}%')
선형회귀모델
sgd_model.fit(X_train,y_train)
r2_score_SGD = sgd_model.score(X_test,y_test)
print(f'r2 score SGD : {r2_score_SGD*100:.2f}%')
7. 예측
선형모델
pred = linear_model.predict(X_test)
r2_score_test = linear_model.score(X_test,y_test)
mse_val = mean_squared_error(y_test,pred)
print(f'R2 score : {r2_score_test*100:.2f}%')
print(f'MSE : {mse_val:.2f}')
R2 score : 71.12%
MSE : 21.52
경사하강모델
pred = sgd_model.predict(X_test)
r2_score_test = sgd_model.score(X_test,y_test)
mse_val = mean_squared_error(y_test,pred)
print(f'R2 score : {r2_score_test*100:.2f}%')
print(f'MSE : {mse_val:.2f}')
R2 score : 71.22%
MSE : 21.44
---> 예측값이 높지는 않다.
---> 하이퍼파라미터 재설정 혹은 데이터 전처리를 다시 할필요가 있다.
---> 여기서는 데이터 전처리를 다시 해주도록 하자(피쳐 새로 추가)
3-2. 전처리
각 컬럼을 모두 곱한 값을 사용한 새로운 컬럼 생성
col = X.columns
for i in range(col.size):
for j in range(i, col.size):
X[col[i] + '*' + col[j]] = X[col[i]] * X[col[j]]
훈련용,테스트용 분할
X_train,X_test,y_train,y_test = train_test_split(X_trans,y,test_size=0.3,random_state=32)#(,shuffle=True)
두번째 훈련및 예측 진행
linear_model2 = LinearRegression()
linear_model2.fit(X_train,y_train)
r2_score2 = linear_model2.score(X_test,y_test)
print(f'R2 score : {r2_score2*100:.2f}%')
R2 score : 86.91%
sgd_model2 = SGDRegressor(eta0=2e-2,max_iter=5000,verbose=0,shuffle=True,random_state=SEED)
sgd_model2.fit(X_train,y_train)
r2_score2 = sgd_model2.score(X_test,y_test)
print(f'R2 score : {r2_score2*100:.2f}%')
R2 score : 83.87%
--> 어느정도 정확도가 올라갔다.
---> 이대로 사용해도 될까?
훈련용,테스트용 분할
X_train,X_test,y_train,y_test = train_test_split(X_trans,y,test_size=0.3,random_state=42)#(,shuffle=True)
R2 score : 66.10%
---> 하지만 Linear모델의 경우 SEED값만 변경해도 예측값이 들쑥날쑥하다.
---> 때문에 Linear모델의 경우 규제를 걸어줄 필요가 있다.
규제 : 선형모델에 가중치에 대해 영향을 주어서 잘 예측하지 못하는 모델이라면 규제를 통하여 모델성능 향상
🔶Ridge 모델 (Linear Regression L2규제를 가한 모델)
- 모든 가중치에 특정 % 만큼의 규제를 가한다
- 모든컬럼을 사용하기는 하지만 0이되는 컬럼은 없다.
- 규제를 가하더라도, 전체 가중치를 전부 사용하기 때문에 전체 데이터가 주로 고루고루 중요할때 사용
- 과대적합보다는 과소적합이거나 일반화에 가까울수록 많이 사용됨
- ----> 특성별 중요도가 차이 없을때 사용(중요한 특정 컬럼이 없을때)
🔶Lasso 모델:(Linear Regression에 L1규제를 가한 모델)
- 규제를 적용할수록 모델이 사용하는 특성의 수를 조절
- 특정 데이터가 중요할 때 사용
- 특성별로 중요도가 다를때, 특정 특성이 중요할 경우 가중치를 다르게 설정하여 특정 데이터가 중요하다 판단될때 사용
- 가중치(기울기)가 0이되는 특성이 생셔서 특성 선택할때, 활용된다.
- ----> 특성별 중요도가 다를때 사용(특정컬럼이 중요할때)
Ridge 모델사용
# 릿지
def ridge_alpha(alpha):
# 모델생성
ridge = Ridge(alpha=alpha)
# 모델학습
ridge.fit(X_train,y_train)
# 훈련용 결과확인
print("훈련결과 : ",ridge.score(X_train,y_train))
# 테스트용 결과확인
print("테스트 결과 : ",ridge.score(X_test,y_test))
ridge_alpha(0.1)
훈련결과 : 0.9402432727947878
테스트 결과 : 0.7352677202363309
alpha값을 증가시킬때는? => 규제를 늘리겠다.
- 모델이 복잡해지는것을 막을때 사용(과대적합일때)
alpha값을 감소시킬때는? => 규제를 줄이겠다.
- 모델이 단순해지는것을 막을때 사용(과소적합일때)
Lasso 모델사용
# 라쏘
def lasso_alpha(alpha):
# 모델생성
lasso = Lasso(alpha=alpha)
# 모델학습
lasso.fit(X_train,y_train)
# 훈련용 결과확인
print("훈련결과 : ",lasso.score(X_train,y_train))
# 테스트용 결과확인
print("테스트 결과 : ",lasso.score(X_test,y_test))
print('사용한특성의수:',np.sum(lasso.coef_!=0))
lasso_alpha(1)
훈련결과 : 0.735148659597438
테스트 결과 : 0.7001176175483983
사용한특성의수: 7
alpha값을 증가시킬때는? => 규제를 늘리겠다.
- 모델이 복잡해지는것을 막을때 사용(과대적합일때)
alpha값을 감소시킬때는? => 규제를 줄이겠다.
- 모델이 단순해지는것을 막을때 사용(과소적합일때)
---> alpha값=1 일때 사용한특성의수: 7개
---> alpha값=0.1 일때 사용한특성의수: 25개
---> alpha값=0.01 일때 사용한특성의수: 63개
---> alpha값=0.01 일때 사용한특성의수: 103개
🔰즉! alpha값으로 사용할 특성의 수를 조절할수있다.
선형분류
Logistic(Sigmoid)
🔶형태
![[Screenshot_277.png]]
🔶수식
$$\text{sigmoid}(x) = \frac{1}{1 + e^{-x}}$$
---> 범위는 0~1사이에 존재하게된다.
🔶Logistic 오차공식 : Cross Entrophy Error
사용이유 : 오차가 0~1사이에 있어서 알아보기 힘들기 때문에 오차를 log화 해서 극대화시켜서 잘 볼수있게 도와준다
![[Screenshot_279.png]]
🔶 수식
$$\mathcal{L} = -\frac{1}{N} \sum_{i=1}^{N} [y_i \log \hat{y}_i + (1 - y_i) \log (1 - \hat{y}_i)]$$
- $y_i$: 실제 레이블 (0 또는 1)
- $\hat{y}_i$: 모델의 예측 확률 (0~1 사이 값)
- $N$: 샘플 개수
---> 오차공식을 사용하여 오차를 극대화 시킨다.
Support Vector Machine (SVM)
🔶개념
서포트 벡터 사이의 거리인 마진을 이용해서 예측하는 모델
🔶형태
![[Screenshot_282 2.png]]
🔶구성요소
◻ 초평면(Hyperplane)
- 데이터를 나누는 선
◻ 마진(Margin)
- 초평면과 가장 가까운 데이터 포인트들 사이의 거리.
◻ 서포트 벡터(Support Vector)
- 마진 경계에 놓여있는 데이터 포인트들
- 이 점들이 초평면의 위치를 결정하는 역할
🔶 장점
- 학습과 예측속도가 매우 빠르다
- 매우 큰 데이터셋에서도 잘 동작
- 특성이 많을수록 잘 동작
🔶단점 - 저차원(특성이 적은) 데이터에서는 별로 좋은성능을 발휘하지 못하는 경향이 있음
🔶혼동행렬
![[Screenshot_288.png]]
쉽게말해
모델이 맞췄는지는 -> True/False
실제타겟 -> Positive/Negative
- TP -> True/Positive
- 모델이 암환자라 예측(예측맞음) /실제 암환자
- TN
- 모델이 정상메일로 예측(예측맞음) / 실제 스팸 정상메일
- FP
- 모델이 범죄자라 예측(예측틀림) /실제 일반사람
- FN
- 모델이 코로나가 아니라고 예측(예측틀림) / 실제 코로나환자
🔶분류 평가지표
◻ Accuracy
전체중에 정확히 맞춘 비율
불균형한 데이터가 들어있을경우 정확도로 성능평가하는것은 문제가됨
◻ Recall
![[Screenshot_295.png]]
![[Screenshot_291.png]]
$$Recall = \frac{TP}{TP+FN}$$
-> FN 을 줄여야 하는경우(암인데 못맞추면 큰일남! 이건 반드시 줄여야함)
🔰 즉! 실제 양성인 데이터 예측을 음성으로 하면 더 큰일날때
사례
- 암진단
- 금융사기판별
- 범죄자 특정
◻ Pricision
![[Screenshot_296.png]]
![[Screenshot_292.png]]
$$Pricision = \frac{TP}{TP+FP}$$
-> FP 을 줄여야 하는경우(스팸메세지 를 받는것보다 중요한 메일을 못받는게 더 문제가될때)
🔰 즉! 실제 음성인 데이터 예측을 양성으로 하면 더 큰일날때
사례
- 스팸메일
- 어린이용 안심가드 영상(안전한 영상 양성/안전하지않는 영상 음성)
◻ F1 Score
![[Screenshot_297.png]]
$$F_1 = 2 \times \frac{\text{Precision} \times \text{Recall}}{\text{Precision} + \text{Recall}}$$
-> recall과 precision의 단점을 보완하기 위해 나온 방법
요약
![[Screenshot_293.png]]
TN : 실제 음성데이터를 음성이라고 맞게 예측한경우 (=정답)
FN : 실제 양성데이터를 음성이라고 잘못 예측한경우 (=오답)
TP : 실제 양성데이터를 양성이라고 맞게 예측한경우 (=오답)
FP : 실제 음성데이터를 양성이라고 잘못 예측한경우 (=오답)
Accuracy : 실제맞춘갯수 / 전체갯수
$$Accuracy = \frac{TP+TN}{TP+FP+TN+FN}$$
Recall : 양성 맞춘데이터 / 실제 양성데이터
$$Recall = \frac{TP}{TP+FN}$$
Precision : 양성 맞춘데이터 / 실제양성 + 실제음성
$$Pricision = \frac{TP}{TP+FP}$$
F1 Score : 정밀도 x 재현률/ 정밀도 + 재현률
$$F_1 = 2 \times \frac{\text{Precision} \times \text{Recall}}{\text{Precision} + \text{Recall}}$$
손글씨 분류 실습
🔰데이터는 이미지데이터를 테이블타입 즉 수치형 데이터로 변환한 상태
1. 환경설정
모듈불러오기,시드고정등
2. 데이터 불러오기
#===========================================================
# 데이터 불러오기
#===========================================================
df = pd.read_csv('./data/손글씨분류/digit_train.csv')
display(df.head(2))
3. 전처리
이미지데이터 -> 2차원 형태로 변경
img0_reshape = img0.values.reshape(28,28)
img0_reshape
데이터분할
X = df.iloc[:,1:]
y= df.iloc[:,0]
X_train, X_test,y_train,y_test = train_test_split(X,y,test_size=3,random_state=SEED,shuffle=True)
4. 데이터분석
시각화
plt.imshow(img0_reshape,cmap='gray')
5. 모델링
# 모델선정
knn_model = KNeighborsClassifier()
logisti_model = LogisticRegression()
svc_model = LinearSVC()
6. 훈련
# 훈련
knn_model.fit(X_train,y_train)
logisti_model.fit(X_train,y_train)
svc_model.fit(X_train,y_train)
7. 예측
# 예측
pred1 = knn_model.predict(X_test)
pred2 = logisti_model.predict(X_test)
pred3 = svc_model.predict(X_test)
# 점수 확인
acc_sc = accuracy_score(y_test,pred3)
print(f'{acc_sc}')
print(classification_report(y_test,pred2))
정확도 : 1.0
classification_report
![[Screenshot_294.png]]
'➕ Data Science > ▹ ML' 카테고리의 다른 글
2. IMDB 영화리뷰 데이터 분류 (2) | 2025.06.02 |
---|---|
1. 텍스트 분석 기초 (2) | 2025.05.23 |
8. 선형분류 (1) | 2025.05.15 |
7. 보스턴주택가격예측 (0) | 2025.05.15 |
6. 선형회귀 (0) | 2025.05.15 |