一
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LinearRegression
from sklearn.ensemble import RandomForestRegressor
import pandas as pd
import zipfile
import re
import numpy as np
import torch
准备工作:
- 安装 sklearn:
python -m pip install scikit-learn -i https://pypi.tuna.tsinghua.edu.cn/simple
清华镜源下载sklearn - 安装 torch:
在清华镜源下安装适配的torch-1.13.0-cp310-cp310-win_amd64.whl。适配要求符合python版本3.10和win10 64位;
cmd中 ①进入conda环境下②在下载的torch文件路径下—通过cd XX实现③输入pip install torch-1.13.0-cp310-cp310-win_amd64.whl 实现下载,如图:
之后才能进行如上导入
二
# 定义解压.zip包函数
def unzip_file(zip_filepath, dest_path):
with zipfile.ZipFile(zip_filepath, 'r') as zip_ref:
zip_ref.extractall(dest_path)
# 对.zip进行解包
unzip_file('used_car_train_20200313.zip','./')
unzip_file('used_car_testB_20200421.zip','./')
准备工作:
- "dest_path is ./“意味着目标路径是当前工作目录(也称为根目录,”."表示当前目录)
- extractall函数作用为解压压缩包中的所有文件至指定文件夹,多个模块都有此函数。
三
test_data = pd.read_csv('used_car_testB_20200421.csv', sep=' ')
train_data = pd.read_csv('used_car_train_20200313.csv', sep=' ')
test_data.to_csv('used_car_testB.csv')
train_data.to_csv('used_car_train.csv')
准备工作:sep是指分割字符
四
data = pd.concat([train_data, test_data])
准备工作——concat函数 pd.concat()
Pandas数据可以实现纵向和横向连接,将数据连接后会形成一个新对象(Series或DataFrame)
连接是最常用的多个数据合并操作
pd.concat()是专门用于数据连接合并的函数,它可以沿着行或列进行操作,同时可以指定非合并轴的合并方式(如合集、交集等)
pd.concat()会返回一个合并后的DataFrame
代码:pd.concat(objs, axis=0, join='outer', ignore_index=False, keys=None, levels=None, names=None, sort=False, verify_integrity=False, copy=True)
参数 :
- objs: 需要连接的数据,可以是多个DataFrame或者Series,它是必传参数
- axis: 连接轴的方法,默认值为0,即按行连接,追加在行后面;值为1时追加到列后面(按列连接:axis=1)
- join: 合并方式,其他轴上的数据是按交集(inner)还是并集(outer)进行合并
- ignore_index: 是否保留原来的索引
- keys: 连接关系,使用传递的键作为最外层级别来构造层次结构索引,就是给每个表指定一个一级索引
- names: 索引的名称,包括多层索引
- verify_integrity: 是否检测内容重复;参数为True时,如果合并的数据与原数据包含索引相同的行,则会报错
- copy: 如果为False,则不要深拷贝
1.按行连接
pd.concat()的基本操作可以实现df.append()功能
操作中ignore_index和sort参数的作用是一样的,axis默认取值为0,即按行连接
import pandas as pd
df1 = pd.DataFrame({'x':[1,2],'y':[3,4]})
df2 = pd.DataFrame({'x':[5,6],'y':[7,8]})
res1 = pd.concat([df1,df2])
2.按列连接
如果要将多个DataFrame按列拼接在一起,可以传入axis=1参数,这会将不同的数据追加到列的后面,索引无法对应的位置上将值填充为NaN
import pandas as pd
df1 = pd.DataFrame({'x':[1,2],'y':[3,4]})
df2 = pd.DataFrame({'x':[5,6,0],'y':[7,8,0]})
res = pd.concat([df1,df2], axis=1)
df1
df2
res
该例子中,df2比df1多一行,合并后df1的部分为NaN
3.合并交集
上述两个练习案例的连接操作会得到两个表内容的并集(默认是join=‘outer’)
合并交集需要将join参数进行改变 join=‘inner’
import pandas as pd
df1 = pd.DataFrame({'x':[1,2],'y':[3,4]})
df2 = pd.DataFrame({'x':[5,6,0],'y':[7,8,0]})
#按列合并交集
#传入join=’inner’取得两个DataFrame的共有部分,去除了df1没有的第三行内容
res = pd.concat([df1,df2], axis=1, join='inner')
df1
df2
res
4.与序列合并
import pandas as pd
z = pd.Series([9,9],name='z')
df = pd.DataFrame({'x':[1,2],'y':[3,4]})
#将序列加到新列
res = pd.concat([df,z],axis=1)
z
df
res
5.指定索引
import pandas as pd
df1 = pd.DataFrame({'x':[1,2],'y':[3,4]})
df2 = pd.DataFrame({'x':[5,6],'y':[7,8]})
#指定索引名
res1 = pd.concat([df1,df2], keys=['a','b'])
#以字典形式传入
dict = {'a':df1, 'b':df2}
res2 = pd.concat(dict)
#横向合并,指定索引
res3 = pd.concat([df1,df2], axis=1, keys=['a','b'])
df1
df2
res1
res2
res3
pandas contact 之后,一定要记得用reset_index去处理index,不然容易出现莫名的逻辑错误 即data=data.reset_index(drop=True)
五
data = data.replace('-', '-1')
data.notRepairedDamage = data.notRepairedDamage.astype('float32')#单拿出某列
data.loc[data['power']>600,'power'] = 600
准备工作:
- replace函数
string.replace( old, new, count )
参数
- old :(必选,字符串类型)被替换的字符串
- new :(必选,字符串类型)替换后的字符串
- count :(可选,整型)替换的次数
返回值: 返回替换后的新字符串
- loc函数
①定位行列:data.loc[行索引, 列名]
②只定位行:data.loc[行索引]
例如:
data.loc[3] 表示第4行的所有内容。
③只定位列:data.loc[:, 列名]
例如:
data.loc[:, “列名1”]
④根据条件定位: data.loc[data[“某个列名”] > 6]
定位某个列值大于6的所有行。
六
cate_cols=['model', 'brand', 'bodyType', 'fuelType', 'gearbox', 'seller', 'notRepairedDamage']
num_cols=['regDate', 'creatDate', 'power', 'kilometer', 'v_0', 'v_1', 'v_2', 'v_3', 'v_4', 'v_5', 'v_6', 'v_7', 'v_8', 'v_9', 'v_10','v_11', 'v_12', 'v_13', 'v_14']
单纯分类一下
七
# 定义One-Hot编码函数
def oneHotEncode(df, colNames):
for col in colNames:
dummies = pd.get_dummies(df[col], prefix=col)
df = pd.concat([df, dummies],axis=1)
df.drop([col], axis=1, inplace=True)
return df
准备工作:
一 , one-hot编码函数
- 什么是one-hot编码?
One-Hot编码,又称为一位有效编码,主要是采用N位状态寄存器来对N个状态进行编码,每个状态都由他独立的寄存器位,并且在任意时候只有一位有效。
One-Hot编码是分类变量作为二进制向量的表示。这首先要求将分类值映射到整数值。然后,每个整数值被表示为二进制向量,除了整数的索引之外,它都是零值,它被标记为1。
- one-hot编码过程详解
比如我们要对 “hello world” 进行one-hot编码,怎么做呢?
①确定要编码的对象–hello world,
②确定分类变量–h e l l o 空格 w o r l d,共27种类别(26个小写字母 + 空格,);
③以上问题就相当于,有11个样本,每个样本有27个特征,将其转化为二进制向量表示,
这里有一个前提,特征排列的顺序不同,对应的二进制向量亦不同(比如我把空格放在第一列和a放第一列,one-hot编码结果肯定是不同的)
因此我们必须要事先约定特征排列的顺序:
- 27种特征首先进行整数编码:a–0,b–1,c–2,…,z–25,空格–26
- 27种特征按照整数编码的大小从前往后排列
get_dummies 是利用pandas实现one hot encode的方式
二,get_dummies函数
pandas.get_dummies(data, prefix=None, prefix_sep='_', dummy_na=False, columns=None, sparse=False, drop_first=False)[source]
例子:
mport pandas as pd
df = pd.DataFrame([
['green' , 'A'],
['red' , 'B'],
['blue' , 'A']])
df.columns = ['color', 'class']
pd.get_dummies(df
get_dummies 前:
get_dummies 后:
上述执行完以后再打印df 出来的还是get_dummies 前的图,因为你没有写df = pd.get_dummies(df)1
- 可以对指定列进行get_dummies
pd.get_dummies(df.color)
- 将指定列进行get_dummies 后合并到元数据中
df = df.join(pd.get_dummies(df.color))1
八
# 处理离散数据
for col in cate_cols:
data[col] = data[col].fillna('-1')
data = oneHotEncode(data, cate_cols)
# 处理连续数据
for col in num_cols:
data[col] = data[col].fillna(0)
data[col] = (data[col]-data[col].min()) / (data[col].max()-data[col].min())
# 处理(可能)无关数据
data.drop(['name', 'regionCode'], axis=1, inplace=True)
data.columns
九
data.to_csv('concat-adress.csv')
十
# 拿出测试集
data=data.reset_index(drop=True)
data = data.astype(float)
test_data = data[pd.isna(data.price)]
X_id=test_data['SaleID']
del test_data['SaleID']
del test_data['price']
X_result=torch.tensor(test_data.values, dtype=torch.float32)
test_data =test_data.astype(float)
test_data.to_csv('one_hot_testB.csv')
# 拿出训练集
train_data = data.drop(data[pd.isna(data.price)].index)
train_data.to_csv('one_hot_train.csv')
y=train_data['price']
del train_data['price']
del train_data['SaleID']
X=torch.tensor(train_data.values, dtype=torch.float32)
y=torch.Tensor(y)
准备工作: astype函数
通过astype
函数显式转换数组的数据类型
十一
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.25,random_state=512)
准备工作—— 机器学习之train_test_split详解
导入方法:
from sklearn.model_selection import train_test_split
读入数据:
X_train,X_test, y_train, y_test =train_test_split(train_data,train_target,test_size=0.25, random_state=0,stratify=y)
参数意义:
- train_data:所要划分的样本特征集
- X_train:划分出的训练数据集数据
- X_test:划分出的测试数据集数据
- y_train:划分出的训练数据集的标签
- y_test:划分出的测试数据集的标签
- train_target:所要划分的样本结果
- test_size:若在0~1之间,为测试集样本数目与原始样本数目之比;若为整数,则是测试集样本的数目
- random_state:是随机数的种子。 随机数种子其实就是该组随机数的编号,在需要重复试验的时候,保证得到一组一样的随机数。比如你每次都填1,其他参数一样的情况下你得到的随机数组是一样的。但填0或不填,每次都会不一样。
- stratify:stratify是为了保持split前类的分布,例如训练集和测试集数量的比例是 A:B=
4:1,等同于split前的比例(80:20)。通常在这种类分布不平衡的情况下会用到stratify。
这一步目的----划分训练集、测试集
将数据集进行拆分,训练集用于模型训练,得到一个大概的模型;测试集用于测试,利用训练集训练出的模型对测试集进行模型预测。
十二
lr1=RandomForestRegressor().fit(X_train,y_train)#随机森林回归模型
lr2=LinearRegression().fit(X_train,y_train)#直线回归模型
print('训练集得分:{:.3f}'.format(lr1.score(X_train,y_train)))
print('测试集得分:{:.3f}'.format(lr1.score(X_test,y_test)))
pred=lr1.predict(X_result)
res=pd.DataFrame(pred, columns=['price'])
X_id=X_id.reset_index(drop=True)
submission = pd.concat([X_id, res['price']], axis=1)
submission.to_csv('submission.csv',index=False)
submission