You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

处理大型CSV文件的内存优化代码故障排查请求

问题排查与修正方案

一、原代码核心问题分析

  1. 内存计算函数f_Size逻辑错误
    原函数通过计算每种数据类型的内存均值再累加,完全不符合内存统计逻辑——正确做法是统计每种类型列的总内存后累加,均值累加无法反映真实内存占用,导致你看不到优化前后的差异。

  2. 数值类型转换逻辑冗余且错误
    在f_Zip函数中,循环每个列时又嵌套循环所有int/float类型,重复对全表同类型列做转换,不仅效率低,还可能导致转换后的列无法正确覆盖到优化后的DataFrame中。

  3. Object转Category的赋值错误
    原代码中xOptimize_File[xFile[xCol]] = xConverted_Object是错误的索引方式,应该直接使用列名xCol来赋值。

  4. 无符号整数转换的风险
    使用downcast="unsigned"会把所有整数转成无符号类型,但如果列中存在负数,会导致数据错误,应该根据列的数值范围选择合适的转换方式。


二、修正后的完整代码

import numpy as np
import pandas as pd
import tkinter as tk
from tkinter import filedialog

xInt_Types = ["int64", "int32", "int16", "int8", "uint64", "uint32", "uint16", "uint8"]
xFloat_Types = ["float64", "float32", "float16"]

# 选择CSV文件
xPath = filedialog.askopenfilename()
xFile = pd.read_csv(xPath)
xColumnName = xFile.columns

# 正确计算DataFrame的总内存占用(单位:MB)
def f_Size(xDataFrame):
    total_bytes = xDataFrame.memory_usage(deep=True).sum()
    return total_bytes / (1024 ** 2)

# 查看数值类型的范围信息
def f_Info(xInt_Types, xFloat_Types):
    for xInt in xInt_Types:
        print(np.iinfo(xInt))
    for xFlt in xFloat_Types:
        print(np.finfo(xFlt))

# 计算DataFrame或单列的内存占用(单位:字节)
def f_M_U(xPandas_Data):
    return xPandas_Data.memory_usage(deep=True).sum() if isinstance(xPandas_Data, pd.DataFrame) else xPandas_Data.memory_usage(deep=True)

# 查看所有Object类型列的统计信息
def f_CSV_Attr(xFile):
    xFile_Object = xFile.select_dtypes(include=["object"])
    if not xFile_Object.empty:
        print(xFile_Object.describe())

# 内存优化核心函数
def f_Zip(xFile):
    xOptimize_File = xFile.copy()
    
    for xCol in xOptimize_File.columns:
        dtype = xOptimize_File[xCol].dtype
        
        # 整数类型优化
        if dtype in xInt_Types:
            # 判断是否有负数,选择有符号/无符号向下转换
            if xOptimize_File[xCol].min() >= 0:
                xOptimize_File[xCol] = pd.to_numeric(xOptimize_File[xCol], downcast="unsigned")
            else:
                xOptimize_File[xCol] = pd.to_numeric(xOptimize_File[xCol], downcast="integer")
        
        # 浮点类型优化
        elif dtype in xFloat_Types:
            xOptimize_File[xCol] = pd.to_numeric(xOptimize_File[xCol], downcast="float")
        
        # Object类型转Category(唯一值占比<50%时)
        elif dtype == "object":
            num_unique = len(xOptimize_File[xCol].unique())
            num_total = len(xOptimize_File[xCol])
            if num_unique / num_total < 0.5:
                xOptimize_File[xCol] = xOptimize_File[xCol].astype("category")
    
    return xOptimize_File

# 输出优化前后的内存占用
print('原始文件内存占用(MB):', round(f_Size(xFile), 4))
xOptimize_File = f_Zip(xFile)
print('优化后文件内存占用(MB):', round(f_Size(xOptimize_File), 4))

三、关键修正说明

  1. 修复内存计算逻辑
    f_Size函数改为直接统计所有列的内存总和,再转换为MB,能准确反映真实内存占用。

  2. 简化数值类型转换
    针对每个列单独处理,根据列的数值范围选择有符号/无符号整数转换,避免重复循环和全表处理,提升效率。

  3. 修复Category赋值错误
    直接使用列名xCol赋值,确保转换后的Category类型列正确替换原列。

  4. 优化Object列统计函数
    f_CSV_Attr改为只统计一次所有Object列,避免重复输出。

内容的提问来源于stack exchange,提问作者Pino

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.13 20:00:05