本文目录导读:

我来详细介绍如何使用Scikit-learn计算R²分数,包括多个实际案例。
基础案例:线性回归的R²分数
import numpy as np
import matplotlib.pyplot as plt
from sklearn.linear_model import LinearRegression
from sklearn.metrics import r2_score
from sklearn.model_selection import train_test_split
# 生成示例数据
np.random.seed(42)
X = np.linspace(0, 10, 100).reshape(-1, 1)
y = 2 * X.ravel() + 1 + np.random.normal(0, 2, 100)
# 划分训练集和测试集
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2, random_state=42)
# 训练线性回归模型
model = LinearRegression()
model.fit(X_train, y_train)
# 预测并计算R²分数
y_pred = model.predict(X_test)
r2 = r2_score(y_test, y_pred)
print(f"R² Score: {r2:.4f}")
print(f"模型解释的方差比例: {r2*100:.2f}%")
# 可视化
plt.figure(figsize=(10, 6))
plt.scatter(X_test, y_test, alpha=0.7, label='实际值')
plt.scatter(X_test, y_pred, alpha=0.7, label='预测值')
plt.plot(X_test, y_pred, 'r-', label='回归线')
plt.xlabel('X')
plt.ylabel('y')f'线性回归结果 (R² = {r2:.4f})')
plt.legend()
plt.grid(True, alpha=0.3)
plt.show()
多元线性回归的R²分数
from sklearn.datasets import load_diabetes
from sklearn.preprocessing import StandardScaler
# 加载糖尿病数据集(包含多个特征)
data = load_diabetes()
X, y = data.data, data.target
feature_names = data.feature_names
print(f"数据集形状: {X.shape}")
print(f"特征名称: {feature_names}")
# 数据标准化
scaler = StandardScaler()
X_scaled = scaler.fit_transform(X)
# 划分数据集
X_train, X_test, y_train, y_test = train_test_split(X_scaled, y, test_size=0.2, random_state=42)
# 训练多元线性回归模型
model = LinearRegression()
model.fit(X_train, y_train)
# 预测并计算R²
y_pred = model.predict(X_test)
r2 = r2_score(y_test, y_pred)
print(f"\n多元线性回归 R² Score: {r2:.4f}")
print(f"调整后的R²: {1 - (1-r2) * (len(y_test)-1) / (len(y_test)-X_test.shape[1]-1):.4f}")
# 分析每个特征的重要性
for i, (name, coef) in enumerate(zip(feature_names, model.coef_)):
print(f"特征 {name}: 系数 = {coef:.4f}")
比较不同模型的R²分数
from sklearn.ensemble import RandomForestRegressor, GradientBoostingRegressor
from sklearn.svm import SVR
from sklearn.metrics import mean_squared_error, mean_absolute_error
# 加载波士顿房价数据集
from sklearn.datasets import fetch_california_housing
housing = fetch_california_housing()
X, y = housing.data, housing.target
# 划分数据
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2, random_state=42)
# 定义要比较的模型
models = {
'Linear Regression': LinearRegression(),
'Random Forest': RandomForestRegressor(n_estimators=100, random_state=42),
'Gradient Boosting': GradientBoostingRegressor(n_estimators=100, random_state=42),
'SVR': SVR(kernel='rbf')
}
# 训练和评估每个模型
results = {}
for name, model in models.items():
model.fit(X_train, y_train)
y_pred = model.predict(X_test)
r2 = r2_score(y_test, y_pred)
mse = mean_squared_error(y_test, y_pred)
mae = mean_absolute_error(y_test, y_pred)
results[name] = {'R²': r2, 'MSE': mse, 'MAE': mae}
print(f"{name}:")
print(f" R² = {r2:.4f}")
print(f" MSE = {mse:.4f}")
print(f" MAE = {mae:.4f}\n")
# 可视化比较
plt.figure(figsize=(12, 6))
models_names = list(results.keys())
r2_scores = [results[name]['R²'] for name in models_names]
bars = plt.bar(models_names, r2_scores, color=['blue', 'green', 'orange', 'red'])
plt.xlabel('模型')
plt.ylabel('R² Score')'不同模型的R²分数比较')
plt.xticks(rotation=45)
# 在柱状图上显示数值
for bar, score in zip(bars, r2_scores):
plt.text(bar.get_x() + bar.get_width()/2, bar.get_height() + 0.01,
f'{score:.4f}', ha='center', va='bottom')
plt.tight_layout()
plt.show()
交叉验证中的R²分数
from sklearn.model_selection import cross_val_score, KFold
from sklearn.preprocessing import PolynomialFeatures
# 创建非线性数据
np.random.seed(42)
X = np.linspace(-3, 3, 100).reshape(-1, 1)
y = 0.5 * X.ravel() ** 2 + X.ravel() + 2 + np.random.normal(0, 1, 100)
# 多项式特征转换
poly = PolynomialFeatures(degree=2)
X_poly = poly.fit_transform(X)
# 使用交叉验证评估R²分数
kfold = KFold(n_splits=5, shuffle=True, random_state=42)
cv_scores = cross_val_score(LinearRegression(), X_poly, y,
cv=kfold, scoring='r2')
print("交叉验证R²分数:")
print(f"每次CV的R²: {cv_scores}")
print(f"平均R²: {cv_scores.mean():.4f} ± {cv_scores.std():.4f}")
# 可视化交叉验证结果
plt.figure(figsize=(10, 5))
plt.plot(range(1, 6), cv_scores, 'bo-', markersize=8)
plt.axhline(y=cv_scores.mean(), color='r', linestyle='--', label=f'平均R² = {cv_scores.mean():.4f}')
plt.fill_between(range(1, 6), cv_scores - cv_scores.std(), cv_scores + cv_scores.std(),
alpha=0.2, color='blue')
plt.xlabel('Fold')
plt.ylabel('R² Score')'5折交叉验证R²分数')
plt.legend()
plt.grid(True, alpha=0.3)
plt.show()
实际案例:房价预测的R²分析
import pandas as pd
from sklearn.compose import ColumnTransformer
from sklearn.pipeline import Pipeline
from sklearn.preprocessing import OneHotEncoder
# 创建一个模拟的房价数据集
np.random.seed(42)
n_samples = 1000
data = pd.DataFrame({
'area': np.random.uniform(50, 200, n_samples),
'bedrooms': np.random.randint(1, 5, n_samples),
'age': np.random.uniform(0, 50, n_samples),
'location': np.random.choice(['center', 'suburb', 'rural'], n_samples),
'price': np.random.uniform(100, 500, n_samples)
})
# 创建特征和目标
X = data.drop('price', axis=1)
y = data['price']
# 划分数据
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.2, random_state=42)
# 创建预处理管道
preprocessor = ColumnTransformer(
transformers=[
('num', StandardScaler(), ['area', 'bedrooms', 'age']),
('cat', OneHotEncoder(drop='first'), ['location'])
])
# 创建完整的管道
pipeline = Pipeline([
('preprocessor', preprocessor),
('regressor', LinearRegression())
])
# 训练模型
pipeline.fit(X_train, y_train)
# 预测并计算R²
y_pred = pipeline.predict(X_test)
r2 = r2_score(y_test, y_pred)
print(f"房价预测模型 R² Score: {r2:.4f}")
print(f"模型解释的变异: {r2*100:.2f}%")
# 残差分析
residuals = y_test - y_pred
plt.figure(figsize=(12, 5))
plt.subplot(1, 2, 1)
plt.scatter(y_pred, residuals, alpha=0.6)
plt.axhline(y=0, color='r', linestyle='--')
plt.xlabel('预测值')
plt.ylabel('残差')f'残差图 (R² = {r2:.4f})')
plt.grid(True, alpha=0.3)
plt.subplot(1, 2, 2)
plt.scatter(y_test, y_pred, alpha=0.6)
plt.plot([y_test.min(), y_test.max()], [y_test.min(), y_test.max()], 'r--', lw=2)
plt.xlabel('实际值')
plt.ylabel('预测值')'实际值 vs 预测值')
plt.grid(True, alpha=0.3)
plt.tight_layout()
plt.show()
R²分数的诊断工具
def r2_analysis(y_true, y_pred, model_name="Model"):
"""
综合分析R²分数及相关指标
"""
r2 = r2_score(y_true, y_pred)
n = len(y_true)
p = 1 # 假设有一个特征
# 调整R²
adj_r2 = 1 - (1 - r2) * (n - 1) / (n - p - 1)
# 其他性能指标
mse = mean_squared_error(y_true, y_pred)
rmse = np.sqrt(mse)
mae = mean_absolute_error(y_true, y_pred)
# 计算预测准确性
mape = np.mean(np.abs((y_true - y_pred) / y_true)) * 100
print(f"{'='*50}")
print(f"{model_name} 性能分析")
print(f"{'='*50}")
print(f"样本数量: {n}")
print(f"特征数量: {p}")
print(f"\nR²分数: {r2:.4f}")
print(f"调整R²: {adj_r2:.4f}")
print(f"MSE: {mse:.4f}")
print(f"RMSE: {rmse:.4f}")
print(f"MAE: {mae:.4f}")
print(f"MAPE: {mape:.2f}%")
print(f"\n解释: R² = {r2:.4f} 意味着模型可以解释 {r2*100:.2f}% 的方差")
return {
'r2': r2,
'adj_r2': adj_r2,
'mse': mse,
'rmse': rmse,
'mae': mae,
'mape': mape
}
# 使用示例
results = r2_analysis(y_test, y_pred, "房价预测模型")
# 诊断信息
if results['r2'] < 0.5:
print("\n⚠️ 警告: R²分数较低,模型性能较差")
elif results['r2'] < 0.8:
print("\n⚠️ 提示: R²分数中等,模型性能可接受")
else:
print("\n✅ R²分数优秀,模型性能良好")
这些案例涵盖了:
- 基础线性回归的R²计算
- 多元线性回归的R²分析
- 不同模型的R²比较
- 交叉验证中的R²评估
- 实际案例应用
- R²诊断工具
记得R²分数的解释:
- R² = 1:完美拟合
- R² > 0.8:优秀拟合
- R² = 0.5-0.8:中等拟合
- R² < 0.5:较差拟合
- R² < 0:模型比简单平均还差
版权声明:NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播