20个Python中pandas数据处理的高级技巧

Written by

in

文章目录
  • 在数据科学和数据分析领域,Python的pandas库已经成为处理结构化数据的标准工具。虽然许多数据科学家和分析师都熟悉pandas的基本操作,但该库中隐藏着许多强大的高级功能,可以显著提高数据处理的效率和灵活性。本文将介绍20个pandas高级技巧,帮助你提升数据处理和分析的能力,让你的代码更加简洁、高效且专业。
  • 下面我们通过一个综合示例,展示如何将这些高级技巧应用到实际数据分析中: import pandas as pd import numpy as np import matplotlib.pyplot as plt import seaborn as sns # 1. 高效读取数据 sales_data = pd.read_csv(‘sales_data.csv’, parse_dates=[‘date’], dtype={‘product_id’: ‘category’, ‘store_id’: ‘category’}) # 2. 数据转换 # 添加时间特征 sales_data[‘year’] = sales_data[‘date’].dt.year sales_data[‘month’] = sales_data[‘date’].dt.month sales_data[‘day_of_week’] = sales_data[‘date’].dt.dayofweek # 3. 高级索引与过滤 # 使用query筛选数据 recent_sales = sales_data.query(‘date >= “2024-01-01” and revenue > 1000’) # 4. 分组操作与聚合 # 按产品和月份分组,计算多个统计量 monthly_stats = sales_data.groupby([‘product_id’, ‘year’, ‘month’]).agg( total_revenue=(‘revenue’, ‘sum’), avg_revenue=(‘revenue’, ‘mean’), total_units=(‘units’, ‘sum’), transaction_count=(‘transaction_id’, ‘nunique’) ).reset_index() # 5. 时间序列处理 # 将数据重采样为周频率 weekly_sales = sales_data.set_index(‘date’).groupby(‘product_id’)[‘revenue’].resample(‘W’).sum() # 计算移动平均 monthly_sales = sales_data.set_index(‘date’)[‘revenue’].resample(‘M’).sum() monthly_sales_smoothed = monthly_sales.rolling(window=3).mean() # 6. 性能优化 # 使用eval计算新列 sales_data = sales_data.eval(‘revenue_per_unit = revenue / units’) # 7. 可视化 plt.figure(figsize=(12, 6)) sns.lineplot(x=monthly_sales.index, y=monthly_sales.values, label=’Monthly Sales’) sns.lineplot(x=monthly_sales_smoothed.index, y=monthly_sales_smoothed.values, label=’3-Month Moving Average’) plt.title(‘Monthly Sales Trend with Moving Average’) plt.xlabel(‘Date’) plt.ylabel(‘Revenue’) plt.legend() plt.tight_layout() plt.show()
  • 掌握这些pandas高级技巧可以显著提高你的数据处理和分析效率。从高效的数据读取和导出,到复杂的数据转换、高级索引、分组聚合、时间序列处理、性能优化和可视化增强,这些技巧涵盖了数据科学工作流程的各个方面。 通过不断实践和应用这些技巧,你将能够编写更简洁、高效和专业的数据分析代码,从而更快地从数据中获取洞察。 以上就是20个Python中pandas数据处理的高级技巧的详细内容,更多关于Python pandas的资料请关注风君子博客其它相关文章! 您可能感兴趣的文章: Python Pandas处理CSV文件的常用技巧分享 Python必备技巧之Pandas数据合并函数 Python数据处理的26个Pandas实用技巧总结 python数据分析必会的Pandas技巧汇总 python使用pandas处理大数据节省内存技巧(推荐) 11个Python Pandas小技巧让你的工作更高效(附代码实例)
  • 目录
    • 引言
    • 1. 高效数据读取与导出
      • 技巧1:使用适当的数据类型
      • 技巧2:分块读取大文件
      • 技巧3:高效导出数据
      • 技巧4:使用SQL查询读取数据
    • 2. 数据转换与重塑
      • 技巧5:使用melt和pivot进行数据重塑
      • 技巧6:使用explode展开列表值
      • 技巧7:使用stack和unstack进行多级索引转换
      • 技巧8:使用map、apply和applymap进行数据转换
    • 3. 高级索引与选择
      • 技巧9:使用.loc和.iloc进行精确索引
      • 技巧10:使用query方法进行高效过滤
      • 技巧11:使用where进行条件替换
      • 技巧12:使用mask进行条件替换
    • 4. 分组操作与聚合
      • 技巧13:使用groupby的高级功能
      • 技巧14:使用transform进行组内转换
      • 技巧15:使用filter筛选组
      • 技巧16:使用pipe构建数据处理管道
    • 5. 时间序列数据处理
      • 技巧17:使用日期范围和频率
      • 技巧18:时间序列重采样
      • 技巧19:时间序列滚动窗口计算
      • 技巧20:时区处理
    • 6. 性能优化技巧
      • 技巧21:使用inplace=True减少内存使用
      • 技巧22:使用numba加速自定义函数
      • 技巧23:使用swifter并行处理
      • 技巧24:使用eval和query进行高性能操作
    • 7. 可视化增强
      • 技巧25:使用内置样式
      • 技巧26:使用styler美化DataFrame显示
      • 技巧27:交互式可视化
    • 8. 综合应用示例
      • 总结

        在数据科学和数据分析领域,Python的pandas库已经成为处理结构化数据的标准工具。虽然许多数据科学家和分析师都熟悉pandas的基本操作,但该库中隐藏着许多强大的高级功能,可以显著提高数据处理的效率和灵活性。本文将介绍20个pandas高级技巧,帮助你提升数据处理和分析的能力,让你的代码更加简洁、高效且专业。

        在读取大型数据集时,指定正确的数据类型可以显著减少内存使用并提高性能:

        import pandas as pd
        import numpy as np
        
        # 定义数据类型字典
        dtypes = {
            'id': np.int32,
            'numeric_col': np.float32,
            'category_col': 'category'
        }
        
        # 读取时指定数据类型
        df = pd.read_csv('large_file.csv', dtype=dtypes)
        

        处理超大文件时,可以使用分块读取避免内存溢出:

        chunks = []
        for chunk in pd.read_csv('huge_file.csv', chunksize=100000):
            # 对每个块进行处理
            processed_chunk = some_processing_function(chunk)
            chunks.append(processed_chunk)
        
        # 合并所有处理过的块
        result = pd.concat(chunks)
        

        导出大型DataFrame时,可以使用更高效的方法:

        # 使用Apache Parquet格式保存数据(需要安装pyarrow)
        df.to_parquet('data.parquet', engine='pyarrow', compression='snappy')
        
        # 使用HDF5格式(需要安装tables)
        df.to_hdf('data.h5', key='df', mode='w')
        

        直接从数据库使用SQL查询读取数据:

        import sqlite3
        
        conn = sqlite3.connect('database.db')
        df = pd.read_sql_query("SELECT * FROM table WHERE column > 5", conn)
        conn.close()
        

        将宽格式数据转换为长格式,反之亦然:

        # 宽格式转长格式
        long_df = pd.melt(
            wide_df, 
            id_vars=['id', 'name'], 
            value_vars=['score1', 'score2', 'score3'],
            var_name='test',
            value_name='score'
        )
        
        # 长格式转宽格式
        wide_df = long_df.pivot(
            index='id',
            columns='test',
            values='score'
        ).reset_index()
        

        将包含列表的单元格展开为多行:

        df = pd.DataFrame({
            'A': [[1, 2, 3], [4, 5], [6]],
            'B': ['a', 'b', 'c']
        })
        
        # 展开A列
        exploded_df = df.explode('A')
        

        处理多级索引数据:

        # 将列索引转为行索引的一部分
        stacked = df.stack()
        
        # 将行索引的一部分转为列索引
        unstacked = stacked.unstack()
        

        不同粒度的数据转换:

        # 对Series中的每个元素应用函数
        df['category'] = df['category'].map({'A': 'Group1', 'B': 'Group2'})
        
        # 对DataFrame的每一行或每一列应用函数
        df['total'] = df[['col1', 'col2']].apply(sum, axis=1)
        
        # 对DataFrame中的每个元素应用函数
        df = df.applymap(lambda x: x.lower() if isinstance(x, str) else x)
        

        高效地选择数据:

        # 基于标签的索引
        subset = df.loc[df['age'] > 30, ['name', 'salary']]
        
        # 基于位置的索引
        first_five_rows_three_cols = df.iloc[0:5, 0:3]
        
        # 混合索引
        mixed_selection = df.loc[df['status'] == 'active', df.columns[2:5]]
        

        使用字符串表达式过滤数据:

        # 传统方法
        filtered_df = df[(df['age'] > 30) & (df['salary'] > 50000)]
        
        # 使用query方法(更易读且通常更快)
        filtered_df = df.query('age > 30 and salary > 50000')
        
        # 使用变量
        min_age = 30
        filtered_df = df.query('age > @min_age')
        

        基于条件替换值:

        # 将不满足条件的值替换为NaN
        df_modified = df.where(df > 0)
        
        # 将不满足条件的值替换为指定值
        df_modified = df.where(df > 0, -1)
        

        与where相反的操作:

        # 将满足条件的值替换为NaN
        df_modified = df.mask(df < 0)
        
        # 将满足条件的值替换为指定值
        df_modified = df.mask(df < 0, 0)
        

        超越基本分组聚合:

        # 多列分组
        result = df.groupby(['department', 'title']).agg({'salary': ['mean', 'median', 'std'], 'age': 'mean'})
        
        # 使用自定义聚合函数
        def iqr(x):
            return x.quantile(0.75) - x.quantile(0.25)
        
        result = df.groupby('department').agg({'salary': [iqr, lambda x: x.max() - x.min()]})
        
        # 使用命名聚合
        result = df.groupby('department').agg(
            avg_salary=('salary', 'mean'),
            max_age=('age', 'max'),
            min_age=('age', 'min')
        )
        

        在不改变DataFrame形状的情况下应用组级别的计算:

        # 添加组平均值列
        df['salary_group_mean'] = df.groupby('department')['salary'].transform('mean')
        
        # 使用自定义转换函数
        df['salary_normalized'] = df.groupby('department')['salary'].transform(lambda x: (x - x.mean()) / x.std())
        
        # 计算组内排名
        df['salary_rank'] = df.groupby('department')['salary'].transform('rank', method='dense')
        

        基于组级别条件筛选数据:

        # 仅保留平均工资超过50000的部门
        high_paying_depts = df.groupby('department').filter(lambda x: x['salary'].mean() > 50000)
        
        # 仅保留至少有10名员工的部门
        large_depts = df.groupby('department').filter(lambda x: len(x) >= 10)
        

        创建可重用的数据处理流程:

        def add_features(df):
            df['salary_to_age_ratio'] = df['salary'] / df['age']
            return df
        
        def filter_outliers(df, column, lower=0.01, upper=0.99):
            lower_bound = df[column].quantile(lower)
            upper_bound = df[column].quantile(upper)
            return df[(df[column] >= lower_bound) & (df[column] <= upper_bound)]
        
        # 构建处理管道
        processed_df = (df
                        .pipe(add_features)
                        .pipe(filter_outliers, 'salary')
                        .pipe(filter_outliers, 'age'))
        

        创建和操作日期序列:

        # 创建日期范围
        date_range = pd.date_range(start='2025-01-01', end='2025-12-31', freq='B')  # B表示工作日
        
        ​​​​​​​# 创建月末日期序列
        month_ends = pd.date_range(start='2025-01-01', periods=12, freq='M')
        
        # 创建季度日期
        quarters = pd.date_range(start='2025-01-01', periods=4, freq='Q')
        

        改变时间序列的频率:

        # 将日数据聚合为月数据
        monthly_data = daily_data.resample('M').mean()
        
        # 将小时数据聚合为日数据,并使用不同的聚合方法
        daily_stats = hourly_data.resample('D').agg({
            'temperature': 'mean',
            'humidity': 'mean',
            'rainfall': 'sum',
            'wind_speed': ['min', 'max', 'mean']
        })
        
        # 将低频数据转换为高频数据(向前填充)
        hourly_data = daily_data.resample('H').ffill()
        

        计算移动平均、累积和等:

        # 7天移动平均
        df['7d_moving_avg'] = df['value'].rolling(window=7).mean()
        
        # 30天指数加权移动平均
        df['30d_ewm'] = df['value'].ewm(span=30).mean()
        
        # 累积计算
        df['cumulative_sum'] = df['value'].cumsum()
        df['cumulative_product'] = df['value'].cumprod()
        
        # 使用自定义窗口函数
        df['rolling_median'] = df['value'].rolling(window=7).apply(lambda x: np.median(x))
        

        处理不同时区的数据:

        # 将时间戳转换为时区感知
        df['timestamp'] = pd.to_datetime(df['timestamp']).dt.tz_localize('UTC')
        
        # 转换时区
        df['local_time'] = df['timestamp'].dt.tz_convert('Asia/Shanghai')
        
        # 移除时区信息
        df['naive_time'] = df['timestamp'].dt.tz_localize(None)
        
        # 在不同时区之间进行日期比较
        mask = (df['timestamp'] >= pd.Timestamp('2025-01-01', tz='UTC')) & 
               (df['timestamp'] <= pd.Timestamp('2025-01-31', tz='UTC'))
        filtered_df = df[mask]
        

        在适当的情况下原地修改数据:

        # 不创建新的DataFrame
        df.fillna(0, inplace=True)
        df.drop('unused_column', axis=1, inplace=True)
        df.reset_index(inplace=True)
        

        注意:虽然inplace=True可以减少内存使用,但在某些情况下可能会降低性能,并且使代码的流式处理变得困难。在现代pandas版本中,推荐的做法是避免使用inplace=True,而是使用方法链。

        对于计算密集型操作,使用numba可以显著提高性能:

        import numba
        
        @numba.jit(nopython=True)
        def fast_calculation(array):
            result = np.zeros_like(array)
            for i in range(len(array)):
                result[i] = some_complex_math(array[i])
            return result
        
        df['result'] = fast_calculation(df['value'].values)
        

        自动并行化pandas操作:

        # 安装:pip install swifter
        import swifter
        
        # 替代普通的apply操作
        df['result'] = df['complex_column'].swifter.apply(complex_function)
        

        对于大型DataFrame,使用这些方法可以避免创建中间对象:

        # 传统方式
        df['C'] = df['A'] + df['B']
        df = df[(df['A'] < 100) & (df['B'] > 50)]
        
        # 高性能方式
        df = df.eval('C = A + B')
        df = df.query('A < 100 and B > 50')
        

        利用pandas的内置样式增强可视化效果:

        # 设置绘图样式
        plt.style.use('ggplot')
        
        # 使用pandas内置绘图功能
        df.plot(kind='bar', figsize=(12, 6))
        
        # 使用多种图表类型
        fig, axes = plt.subplots(2, 2, figsize=(12, 10))
        df.plot(kind='line', ax=axes[0, 0], title='Line Plot')
        df.plot(kind='bar', ax=axes[0, 1], title='Bar Plot')
        df.plot(kind='box', ax=axes[1, 0], title='Box Plot')
        df.plot(kind='scatter', x='A', y='B', ax=axes[1, 1], title='Scatter Plot')
        

        在Jupyter Notebook中美化DataFrame的显示:

        # 高亮最大值
        styled_df = df.style.highlight_max(color='lightgreen')
        
        # 根据条件设置样式
        styled_df = df.style.applymap(lambda x: 'background-color: yellow' if x < 0 else '')
        
        # 使用渐变颜色
        styled_df = df.style.background_gradient(cmap='viridis')
        
        # 格式化数值
        styled_df = df.style.format({
            'A': '{:.2f}',
            'B': '{:+.2f}',
            'C': '{:.2%}'
        })
        

        结合其他库创建交互式可视化:

        # 使用plotly(需要安装plotly)
        import plotly.express as px
        fig = px.line(df, x='date', y='value', color='category')
        fig.show()
        
        # 使用hvplot(需要安装hvplot和holoviews)
        import hvplot.pandas
        interactive_plot = df.hvplot.scatter(x='A', y='B', by='category', hover_cols=['C', 'D'])
        

        下面我们通过一个综合示例,展示如何将这些高级技巧应用到实际数据分析中:

        import pandas as pd
        import numpy as np
        import matplotlib.pyplot as plt
        import seaborn as sns
        
        # 1. 高效读取数据
        sales_data = pd.read_csv('sales_data.csv', 
                                 parse_dates=['date'],
                                 dtype={'product_id': 'category', 'store_id': 'category'})
        
        # 2. 数据转换
        # 添加时间特征
        sales_data['year'] = sales_data['date'].dt.year
        sales_data['month'] = sales_data['date'].dt.month
        sales_data['day_of_week'] = sales_data['date'].dt.dayofweek
        
        # 3. 高级索引与过滤
        # 使用query筛选数据
        recent_sales = sales_data.query('date >= "2024-01-01" and revenue > 1000')
        
        # 4. 分组操作与聚合
        # 按产品和月份分组,计算多个统计量
        monthly_stats = sales_data.groupby(['product_id', 'year', 'month']).agg(
            total_revenue=('revenue', 'sum'),
            avg_revenue=('revenue', 'mean'),
            total_units=('units', 'sum'),
            transaction_count=('transaction_id', 'nunique')
        ).reset_index()
        
        # 5. 时间序列处理
        # 将数据重采样为周频率
        weekly_sales = sales_data.set_index('date').groupby('product_id')['revenue'].resample('W').sum()
        
        # 计算移动平均
        monthly_sales = sales_data.set_index('date')['revenue'].resample('M').sum()
        monthly_sales_smoothed = monthly_sales.rolling(window=3).mean()
        
        # 6. 性能优化
        # 使用eval计算新列
        sales_data = sales_data.eval('revenue_per_unit = revenue / units')
        
        # 7. 可视化
        plt.figure(figsize=(12, 6))
        sns.lineplot(x=monthly_sales.index, y=monthly_sales.values, label='Monthly Sales')
        sns.lineplot(x=monthly_sales_smoothed.index, y=monthly_sales_smoothed.values, label='3-Month Moving Average')
        plt.title('Monthly Sales Trend with Moving Average')
        plt.xlabel('Date')
        plt.ylabel('Revenue')
        plt.legend()
        plt.tight_layout()
        plt.show()
        

        掌握这些pandas高级技巧可以显著提高你的数据处理和分析效率。从高效的数据读取和导出,到复杂的数据转换、高级索引、分组聚合、时间序列处理、性能优化和可视化增强,这些技巧涵盖了数据科学工作流程的各个方面。

        通过不断实践和应用这些技巧,你将能够编写更简洁、高效和专业的数据分析代码,从而更快地从数据中获取洞察。

        以上就是20个Python中pandas数据处理的高级技巧的详细内容,更多关于Python pandas的资料请关注风君子博客其它相关文章!

        您可能感兴趣的文章:

        • Python Pandas处理CSV文件的常用技巧分享
        • Python必备技巧之Pandas数据合并函数
        • Python数据处理的26个Pandas实用技巧总结
        • python数据分析必会的Pandas技巧汇总
        • python使用pandas处理大数据节省内存技巧(推荐)
        • 11个Python Pandas小技巧让你的工作更高效(附代码实例)

        站内搜索