机器学习之python文件读取
一、read_sql与to_sql函数
1.1 read_sql函数
- 读取数据一般是从数据库中读取的,因此在read_sql()函数中填写相应的SQL语句来读取我们想要的数据
- pd.read_sql(sql, con, index_col=None, coerce_float=True, params=None, parse_dates=None, columns=None, chunksize=None)
1)sql: SQL命令字符串;
2)con: 连接SQL数据库的Engine,一般用SQLAlchemy或者是PyMysql之类的模块来建立;
3)index_col:选择某一列作为Index;
4)coerce_float:将数字形式的字符串直接以float型读入;
5)parse_dates: 将某一列日期型字符串转换为datatime型数据,可以直接提供需要转换的列名以默认的日期形式转换,或者也可以提供字典形式的列名和转换日期的格式;
#采用pymysql模块建立数据库连接,并读取数据库中的数据
import pandas as pd
from pymysql import *
conn=connect(host='localhost',port=3306, database='database_name', user='root', password='123456',charset='utf8')
#host是连接数据库的主机IP地址,mysql默认端口是3306,database是数据库的名称,user和password分别是连接数据库的账号和密码,charset是数据库字符编码
#写一条SQL语句,采用read_sql()函数来读取
sql_cmd='SELECT * FROM table_name'
df=pd.read_sql(sql_cmd, conn)
df.head()
#测试下参数parse_dates的作用
sql_cmd_2 = "SELECT * FROM test_date"
df_1 = pd.read_sql(sql_cmd_2, conn)
df_1.head()
"""
output
number date_columns
0 1 2021-11-11
1 2 2021-10-01
2 3 2021-11-10
"""
df_1.info()
"""
<class 'pandas.core.frame.DataFrame'>
RangeIndex: 3 entries, 0 to 2
Data columns (total 2 columns):
# Column Non-Null Count Dtype
--- ------ -------------- -----
0 number 3 non-null int64
1 date_columns 3 non-null object
dtypes: int64(1), object(1)
memory usage: 176.0+ bytes
"""
#正常默认情况下,date_columns这一列也是被当做是String类型的数据,要是我们通过parse_dates参数将日期解析应用与该列
df_2 = pd.read_sql(sql_cmd_2, conn, parse_dates="date_columns")
df_2.info()
"""
<class 'pandas.core.frame.DataFrame'>
RangeIndex: 3 entries, 0 to 2
Data columns (total 2 columns):
# Column Non-Null Count Dtype
--- ------ -------------- -----
0 number 3 non-null int64
1 date_columns 3 non-null datetime64[ns]
dtypes: datetime64[ns](1), int64(1)
memory usage: 176.0 bytes
"""
#就转换成了相对应的日期格式,当然我们还可以采用上面提到的另外一种格式
parse_dates={"date_column": {"format": "%d/%m/%y"}}
df_3 = pd.read_sql(sql_cmd_2, conn, parse_dates=parse_dates)
df_3.info()
1.2 to_sql函数
- DataFrame.to_sql(name,con,schema=None,if_exists=‘fail’,index=True, index_label=None,chunksize=None,dtype=None,method=None)
1)name:是输入数据库中的表名;
2)con:与数据库链接的方式,推荐使用sqlalchemy的engine类型;
3)schema: 相应数据库的引擎,不设置则使用数据库的默认引擎,如mysql中的innodb引擎;
4)if_exists: 当数据库中已经存在数据表时对数据表的操作,有replace替换、append追加,fail则当表存在时提示ValueError;
5)index:对DataFrame的index索引的处理,为True时索引也将作为数据写入数据表;
6)index_label:当上一个参数index为True时,设置写入数据表时index的列名称;
7)chunsize:设置整数,如20000,一次写入数据时的数据行数量,当数据量很大时,需要设置,否则会链接超时写入失败;
8)dtype:写入数据表时,可以设置列的名称(The keys should be the column names and the values should be the SQLAlchemy types or strings for the sqlite3 legacy mode),需要设置时,类型需要和sqlalchemy的类型保持一致.当不设置时,to_sql生成表时会自动兼容最大的类型; - to_sql()参数中除 name、con必填外,可选参数index推荐使用False,同时dtype推荐不使用。
- to_sql方法当数据表不存在时创建,存在时根据if_exists参数设置的replace,append,fail时分别对应替换、追加、失败处理。
#sqlalchemy.create_engine()函数创建engine的两种方式:
from sqlalchemy import create_engine
engine = create_engine('mysql+mysqldb://user:passwd@127.0.0.1/database?charset=utf8')
engine = create_engine('mysql+mysqlconnector:// user:passwd@127.0.0.1/database?charset=utf8')
#user:passwd@127.0.0.1/database --> 格式为 用户名:密码@服务器地址/数据库名
from sqlalchemy import create_engine
DB_STRING = 'mysql+mysqlconnector://user:passwd@127.0.0.1/database?charset=utf8'
engine = create_engine(DB_STRING)
data.to_sql('表名',con = engine)
#这种使用方式在mysql5.7版本以前,是没有问题,但是在mysql8版本以后,mysql8更改了密码加密方式,在使用此种方式时会提示错误。
#在用to_sql写入mysql8以上版本时,需要使用mysqldb作为驱动
#在导入pymysql使用时需要pymysql.install_as_MySQLdb()才能使用
import pymysql
pymysql.install_as_MySQLdb()
DB_STRING = 'mysql+mysqldb://user:passwd@127.0.0.1/db_name?charset=utf8'
engine = create_engine(DB_STRING)
data.to_sql('表名',con = engine)
#参数dtype使用方法
#DATE,CHAR,VARCHAR… 可以去 sqlalchemy 的官方文档查看所有的sql数据类型: [‘TypeEngine’, ‘TypeDecorator’, ‘UserDefinedType’, ‘INT’, ‘CHAR’, ‘VARCHAR’, ‘NCHAR’, ‘NVARCHAR’, ‘TEXT’, ‘Text’, ‘FLOAT’, ‘NUMERIC’, ‘REAL’, ‘DECIMAL’, ‘TIMESTAMP’, ‘DATETIME’, ‘CLOB’, ‘BLOB’, ‘BINARY’, ‘VARBINARY’, ‘BOOLEAN’, ‘BIGINT’, ‘SMALLINT’, ‘INTEGER’, ‘DATE’, ‘TIME’, ‘String’, ‘Integer’, ‘SmallInteger’, ‘BigInteger’, ‘Numeric’, ‘Float’, ‘DateTime’, ‘Date’, ‘Time’, ‘LargeBinary’, ‘Binary’, ‘Boolean’, ‘Unicode’, ‘Concatenable’, ‘UnicodeText’, ‘PickleType’, ‘Interval’, ‘Enum’, ‘Indexable’, ‘ARRAY’, ‘JSON’] 可以选择合适的类型与数据库对应
from sqlalchemy.types import DATE,CHAR,VARCHAR
DTYPES = {'col_1字段名称' : DATE, 'col_2':CHAR(4),'col_3':VARCHAR(10)}
df.to_sql('表名',con = engine,dtype = DTYPES)
#将写入数据表的df中,dtype 指定 根据列名对应的数据类型字段即可
#执行SQL语句查看写入的数据库数据情况
engine.execute("SELECT * FROM table_name").fetchall()
二、from_dict函数和to_dict函数
2.1 from_dict函数
a_dict = {
'学校': '清华大学',
'地理位置': '北京',
'排名': 1
}
df = pd.json_normalize(a_dict) #字典格式的数据转换为DataFrame
df
df = pd.DataFrame(a_dict, index = [0])#字典格式的数据转换为DataFrame
df
df = pd.DataFrame.from_dict(a_dict,orient='index')#字典格式的数据转换为DataFrame
df
data = {'col_1': [1, 2, 3, 4],
'col_2': ['A', 'B', 'C', 'D']}
df = pd.DataFrame.from_dict(data, orient='columns')#字典格式的数据转换为DataFrame
df
df = pd.DataFrame.from_dict(data, orient='index')#字典格式的数据转换为DataFrame
df
2.2 to_dict函数
- to_dict(orient):orient取值有dict(默认)、list、split、records、index
df = pd.DataFrame({'shape': ['square', 'circle', 'triangle'],
'degrees': [360, 360, 180],
'sides': [4, 5, 3]})
df
- 输出为dict:orient取值为’dict’
#输出为dict
dict_out=df.to_dict(orient='dict')
dict_out
#输出
"""
{'shape': {0: 'square', 1: 'circle', 2: 'triangle'},
'degrees': {0: 360, 1: 360, 2: 180},
'sides': {0: 4, 1: 5, 2: 3}}
"""
#读取
df=pd.DataFrame.from_dict(dict_out)
df
#结果
"""
shape degrees sides
0 square 360 4
1 circle 360 5
2 triangle 180 3
"""
- 输出为dict:orient取值为’split’
#输出为dict
dict_out=df.to_dict(orient='split')
dict_out
#输出
"""
{'index': [0, 1, 2],
'columns': ['shape', 'degrees', 'sides'],
'data': [['square', 360, 4], ['circle', 360, 5], ['triangle', 180, 3]]}
"""
#读取
df=pd.DataFrame.from_dict(dict_out)
df
#结果
"""
index columns data
0 0 shape [square, 360, 4]
1 1 degrees [circle, 360, 5]
2 2 sides [triangle, 180, 3]
"""
- 输出为dict:orient取值为’list’
#输出为dict
dict_out=df.to_dict(orient='list')
dict_out
#输出
"""
{'shape': ['square', 'circle', 'triangle'],
'degrees': [360, 360, 180],
'sides': [4, 5, 3]}
"""
#读取
df=pd.DataFrame.from_dict(dict_out)
df
#结果
"""
shape degrees sides
0 square 360 4
1 circle 360 5
2 triangle 180 3
"""
- 输出为dict:orient取值为’index’
#输出为dict
dict_out=df.to_dict(orient='index')
dict_out
#输出
"""
{0: {'index': 0, 'columns': 'shape', 'data': ['square', 360, 4]},
1: {'index': 1, 'columns': 'degrees', 'data': ['circle', 360, 5]},
2: {'index': 2, 'columns': 'sides', 'data': ['triangle', 180, 3]}}
"""
- 输出为dict:orient取值为’records’
#输出为dict
dict_out=df.to_dict(orient='records')
dict_out
#输出
"""
[{0: 0, 1: 1, 2: 2},
{0: 'shape', 1: 'degrees', 2: 'sides'},
{0: ['square', 360, 4], 1: ['circle', 360, 5], 2: ['triangle', 180, 3]}]
"""
三、read_json函数和to_json函数
3.1 read_json函数
-
pandas.read_json()
1)参数orient:对应JSON字符串的格式
2)split: 格式类似于:{index: [index], columns: [columns], data: [values]}
3)records: 格式类似于:[{column: value}, … , {column: value}]
4)index: 格式类似于:{index: {column: value}}
5)columns: 格式类似于:{column: {index: value}}
6)values: 数组 -
split格式:格式类似于:{index: [index], columns: [columns], data: [values]}
import pandas as pd
#split: 格式类似于:{index: [index], columns: [columns], data: [values]}
#例如我们的JSON字符串长这样
a='{"index":[1,2,3],"columns":["a","b"],"data":[[1,3],[2,8],[3,9]]}'
df = pd.read_json(a, orient='split')
df
#输出
"""
a b
1 1 3
2 2 8
3 3 9
"""
- records格式:类似于:[{column: value}, … , {column: value}]
import pandas as pd
#例如我们的JSON字符串长这样
#records: 格式类似于:[{column: value}, ... , {column: value}]
#例如我们的JSON字符串长这样
a = '[{"name":"Tom","age":"18"},{"name":"Amy","age":"20"},{"name":"John","age":"17"}]'
df_1 = pd.read_json(a, orient='records')
df_1
#输出
"""
name age
0 Tom 18
1 Amy 20
2 John 17
"""
- index格式:类似于:{index: {column: value}}
import pandas as pd
#例如我们的JSON字符串长这样
#index: {index: {column: value}}
#例如我们的JSON字符串长这样
a = '{"index_1":{"name":"John","age":20},"index_2":{"name":"Tom","age":30},"index_3":{"name":"Jason","age":50}}'
df_1 = pd.read_json(a, orient='index')
df_1
#输出
"""
name age
index_1 John 20
index_2 Tom 30
index_3 Jason 50
"""
- columns格式: 格式类似于:{column: {index: value}}
import pandas as pd
#columns: 格式类似于:{column: {index: value}}
a = '{"index_1":{"name":"John","age":20},"index_2":{"name":"Tom","age":30},"index_3":{"name":"Jason","age":50}}'
df_1 = pd.read_json(a, orient='columns')
df_1
#输出
"""
index_1 index_2 index_3
name John Tom Jason
age 20 30 50
"""
- values数组
import pandas as pd
#values: 数组
#例如我们的JSON字符串长这样
v='[["a",1],["b",2],["c", 3]]'
df_1 = pd.read_json(v, orient="values")
df_1
#输出
"""
0 1
0 a 1
1 b 2
2 c 3
"""
3.2 to_json函数
- 将DataFrame数据对象输出成JSON字符串,可以使用to_json()方法来实现,其中orient参数可以输出不同格式的字符串,用法和上面的大致相同
四、read_html函数和to_html函数
4.1 read_html函数
- 有时候我们需要抓取网页上面的一个表格信息,相比较使用Xpath或者是Beautifulsoup,我们可以使用pandas当中已经封装好的函数read_html来快速地进行获取,例如我们通过它来抓取菜鸟教程Python网站上面的一部分内容
#!pip3 install lxml #第一次使用read_html时,需安装lxml包
from lxml import *
url = "https://www.runoob.com/python/python-exceptions.html"
dfs = pd.read_html(url, header=None, encoding='utf-8')#返回是一个list
df=dfs[0]
df.head()
#输出
"""
异常名称 描述
0 NaN NaN
1 BaseException 所有异常的基类
2 SystemExit 解释器请求退出
3 KeyboardInterrupt 用户中断执行(通常是输入^C)
4 Exception 常规错误的基类
"""
4.2 to_html函数
import numpy as np
df = pd.DataFrame(np.random.randn(3, 3),columns=['A','B','C'])
df.to_html("test_1.html",index=False)
dfs = pd.read_html("test_1.html")
dfs[0]
#输出
"""
A B C
0 -0.348165 -0.572741 -0.190966
1 0.700785 -0.848750 -1.853054
2 0.941161 -0.944569 0.749450
"""
五、read_csv函数和to_csv函数
5.1 read_csv函数
#参数filepath_or_buffer:数据输入的路径,可以是URL
#sep: 读取csv文件时指定的分隔符,默认为逗号
#index_col: 我们在读取文件之后,可以指定某一列作为DataFrame的索引
pd.read_csv(filepath_or_buffer='data.csv',index_col=0)
#输出
"""
num1 num2 num3 num4
0 1 2 3 4
1 6 12 7 9
2 11 13 15 18
3 12 10 16 18
"""
#index_col除了指定单个列,我们还可以指定多个列
pd.read_csv(filepath_or_buffer='data.csv',index_col=['num1','num2'])
#输出
Unnamed: 0 num3 num4
num1 num2
1 2 0 3 4
6 12 1 7 9
11 13 2 15 18
12 10 3 16 18
#usecols:如果数据集当中的列很多,而我们并不想要全部的列、而是只要指定的列就可以,就可以使用这个参数
#pd.read_csv('data.csv', usecols=["列名1", "列名2", ....])
pd.read_csv('data.csv', usecols=["num1", "num2"])
#输出
num1 num2
0 1 2
1 6 12
2 11 13
3 12 10
#usecols除了指定列名之外,也可以通过索引来选择想要的列,示例代码如下
df = pd.read_csv("data.csv", usecols = [1, 2])
df
#输出
num1 num2
0 1 2
1 6 12
2 11 13
3 12 10
#usecols参数能够接收一个函数,将列名作为参数传递到该函数中调用,要是满足条件的,就选中该列,反之则不选择该列
pd.read_csv("data.csv", usecols = lambda x:len(x)<5)
#输出
num1 num2 num3 num4
0 1 2 3 4
1 6 12 7 9
2 11 13 15 18
3 12 10 16 18
#prefix: 当导入的数据没有header的时候,可以用来给列名添加前缀
pd.read_csv("data.csv", prefix="test_", header = None)
#输出
test_0 test_1 test_2 test_3 test_4
0 NaN num1 num2 num3 num4
1 0.0 1 2 3 4
2 1.0 6 12 7 9
3 2.0 11 13 15 18
4 3.0 12 10 16 18
#skiprows: 过滤掉哪些行,参数当中填行的索引
pd.read_csv("data.csv", skiprows=[0, 1])
#上面的代码过滤掉了前两行的数据,直接将第三行与第四行的数据输出,可以看到第二行的数据被当成了表头
#输出
1 6 12 7 9
0 2 11 13 15 18
1 3 12 10 16 18
#nrows: 该参数设置一次性读入的文件行数,对于读取大文件时非常有用,比如 16G 内存的PC无法容纳几百G的大文件
pd.read_csv("data.csv", nrows=2)
#输出
Unnamed:0 num1 num2 num3 num4
0 0 1 2 3 4
1 1 6 12 7 9
5.2 to_csv函数
5.2.1 保存csv格式
#该方法主要是用于将DataFrame写入csv文件当中,示例代码如下
df=pd.read_csv("data.csv", usecols = lambda x:len(x)<5)
df.to_csv("文件名.csv", index = False)
5.2.2 保存zip格式
#我们还能够输出到zip文件的格式
df = pd.read_csv("data.csv")
compression_opts = dict(method='zip',
archive_name='output.csv')
df.to_csv('output.zip', index=False,
compression=compression_opts)
六、read_excel函数和to_excel函数
6.1 read_excel函数
#! pip install xlrd #第一次执行read_excel时,需要进行安装xlrd包
#!pip install openpyxl #第一次执行read_excel时,需要进行安装openpyxl包
df = pd.read_excel("data.xlsx",engine='openpyxl') #由于xlrd包的版本问题,所以必须添加engine='openpyxl'
df
#输出
Unnamed: 0 num1 num2 num3 num4
0 0 1 2 3 4
1 1 6 12 7 9
2 2 11 13 15 18
3 3 12 10 16 18
#dtype: 该参数能够对指定某一列的数据类型加以设定
df = pd.read_excel("data.xlsx",engine='openpyxl',dtype={'Unnamed: 0': str, 'num1': float})
print(df.info())
df
#输出
<class 'pandas.core.frame.DataFrame'>
RangeIndex: 4 entries, 0 to 3
Data columns (total 5 columns):
# Column Non-Null Count Dtype
--- ------ -------------- -----
0 Unnamed: 0 4 non-null object
1 num1 4 non-null float64
2 num2 4 non-null int64
3 num3 4 non-null int64
4 num4 4 non-null int64
dtypes: float64(1), int64(3), object(1)
memory usage: 288.0+ bytes
None
Unnamed: 0 num1 num2 num3 num4
0 0 1.0 2 3 4
1 1 6.0 12 7 9
2 2 11.0 13 15 18
3 3 12.0 10 16 18
#heet_name: 对于读取excel当中的哪一个sheet当中的数据加以设定
df = pd.read_excel("data.xlsx",engine='openpyxl', sheet_name="Sheet2")
df
#输出
Unnamed: 0 num5 num6 num7 num8
0 0 1 2 3 4
1 1 6 12 7 9
2 2 11 13 15 18
3 3 12 10 16 18
#当然我们要是想一次性读取多个Sheet当中的数据也是可以的,最后返回的数据是以dict形式返回的
df = pd.read_excel("data.xlsx",engine='openpyxl',sheet_name=["Sheet1", "Sheet2"])
df
#输出
{'Sheet1': Unnamed: 0 num1 num2 num3 num4
0 0 1 2 3 4
1 1 6 12 7 9
2 2 11 13 15 18
3 3 12 10 16 18,
'Sheet2': Unnamed: 0 num5 num6 num7 num8
0 0 1 2 3 4
1 1 6 12 7 9
2 2 11 13 15 18
3 3 12 10 16 18}
#例如我们只想要Sheet1的数据,可以使用get函数
df.get("Sheet1")
#输出
Unnamed: 0 num1 num2 num3 num4
0 0 1 2 3 4
1 1 6 12 7 9
2 2 11 13 15 18
3 3 12 10 16 18
6.2 to_excel函数
#将DataFrame对象写入Excel表格,除此之外还有ExcelWriter()方法也有着异曲同工的作用
df1 = pd.DataFrame([['A', 'B'], ['C', 'D']],
index=['Row 1', 'Row 2'],
columns=['Col 1', 'Col 2'])
df1.to_excel("output1.xlsx")
#指定Sheet的名称
df1.to_excel("output1.xlsx", sheet_name='Sheet_Name_1_1_1')
#将多个DataFrame数据集输出到一个Excel当中的不同的Sheet当中
df2 = df1.copy()
with pd.ExcelWriter('output2.xlsx') as writer:
df1.to_excel(writer, sheet_name='Sheet_name_1_1_1')
df2.to_excel(writer, sheet_name='Sheet_name_2_2_2')
#在现有的Sheet的基础之上,再添加一个Sheet
df3 = df1.copy()
with pd.ExcelWriter('output2.xlsx', mode="a", engine="openpyxl") as writer:
df3.to_excel(writer, sheet_name='Sheet_name_3_3_3')
#mode参数有w和a两种,w是覆盖写入,将会覆盖原有的Sheet,a是追加写入append,重新添加一个Sheet
#可以生成至Excel文件并且进行压缩包处理
import zipfile
with zipfile.ZipFile("output_excel.zip", "w") as zf:
with zf.open("output_excel.xlsx", "w") as buffer:
with pd.ExcelWriter(buffer) as writer:
df1.to_excel(writer)
#对于日期格式或者是日期时间格式的数据,也能够进行相应的处理
from datetime import date, datetime
df = pd.DataFrame(
[
[date(2019, 1, 10), date(2021, 11, 24)],
[datetime(2019, 1, 10, 23, 33, 4), datetime(2021, 10, 20, 13, 5, 13)],
],
index=["Date", "Datetime"],
columns=["X", "Y"])
df
#输出
X Y
Date 2019-01-10 00:00:00 2021-11-24 00:00:00
Datetime 2019-01-10 23:33:04 2021-10-20 13:05:13
#根据日期格式进行存储写入
with pd.ExcelWriter(
"output_excel_date.xlsx",
date_format="YYYY-MM-DD",
datetime_format="YYYY-MM-DD HH:MM:SS"
) as writer:
df.to_excel(writer)
七、read_table函数
- 对于txt文件,既可以用read_csv()方法来读取,也可以用read_table()方法来读取,其中的参数和read_csv()当中的参数大致相同
#读取以空格隔开的数据
import pandas as pd
df = pd.read_table('sentences.txt',header=None, encoding='utf8') #enconding='utf8'不加时,中文会显示乱码
df
#输出
0
0 我爱你中国!
1 中国伟大,祖国平安!
2 人民幸福!
八、read_pickle函数和to_pickle函数
- Python当中的Pickle模块实现了对一个Python对象结构的二进制序列和反序列化,序列化过程是将文本信息转变为二进制数据流,同时保存数据类型。例如数据处理过程中,突然有事儿要离开,可以直接将数据序列化到本地,这时候处理中的数据是什么类型,保存到本地也是同样的类型,反序列化之后同样也是该数据类型,而不是从头开始处理。
8.1 read_pickle函数
from datetime import date, datetime
df = pd.DataFrame(
[
[date(2019, 1, 10), date(2021, 11, 24)],
[datetime(2019, 1, 10, 23, 33, 4), datetime(2021, 10, 20, 13, 5, 13)],
],
index=["Date", "Datetime"],
columns=["X", "Y"])
df.to_pickle('test.pkl')
df
#结果
X Y
Date 2019-01-10 00:00:00 2021-11-24 00:00:00
Datetime 2019-01-10 23:33:04 2021-10-20 13:05:13
8.2 to_pickle函数
df2 = pd.read_pickle("test.pkl")
df2
#结果
X Y
Date 2019-01-10 00:00:00 2021-11-24 00:00:00
Datetime 2019-01-10 23:33:04 2021-10-20 13:05:13
九、read_clipboard函数和to_clipboard函数
9.1 read_clipboard函数
- 有时候数据获取不太方便,我们可以通过复制的方式,在电脑的任意一个地方成功复制数据后,可通过Pandas当中的read_clipboard()方法来读取复制成功的数据
df=pd.read_clipboard()
df
#结果
X Y
Date 2019-01-10 00:00:00 2021-11-24 00:00:00
Datetime 2019-01-10 23:33:04 2021-10-20 13:05:13
to_clipboard函数
- 有复制就会有粘贴,我们可以将DataFrame数据集输出至剪贴板中
df.to_clipboard()