如何读取CSV后基于列名字符串存在性创建新列及函数返回None异常排查
返回None的核心原因拆解
你遇到的问题和“新列赋值步骤”没有直接关联,是多层错误叠加、被无差别捕获的裸except静默吞错,加上函数本身缺失返回逻辑共同导致的,逐行排查的问题点如下:
- 基础语法/API调用错误(代码从读文件阶段就抛出异常,根本走不到列赋值步骤)
- 路径拼接写法违规:原代码写的
os.path.join(path1, path2/{id}/{year})不符合Python字符串规范,无法在普通字符串中直接嵌入变量占位符,最终生成的路径格式错误、没有替换id、year的实际值,读文件阶段直接抛出FileNotFoundError - pandas读文件API调用错误:原代码
new_df = pd.read(csv(path, low_memory=False)存在两个硬伤:一是pandas没有pd.read通用读文件方法,读CSV的正确方法是pd.read_csv();二是括号未闭合,直接触发语法解析错误,代码根本无法启动运行 - 列表推导式变量名错位:
col_name_3 = [col for col in new_df.columns if all (sub in column for sub in subs_2)]循环定义的匹配变量是col,判断逻辑里却引用了不存在的column变量,触发NameError - 函数返回值缺失:原函数在try块内完成所有DataFrame操作后,没有显式写
return new_df逻辑,哪怕所有步骤全程无异常运行,函数执行到末尾也会因为没有显式返回值,默认返回None,这是拿到NoneType结果的核心原因之一
- 路径拼接写法违规:原代码写的
- 列赋值逻辑错误(这是你误以为“加了赋值就出问题”的核心原因)
你通过列表推导式生成的col_name_1、col_name_2、col_name_3本质是所有匹配目标列名组成的列表,而非单个列名。比如匹配含“product”关键字的列如果有2个,new_df[col_name_1]返回的是2列宽度的DataFrame,你直接把这个多列结构赋值给单个新列new_df["col_name_1"],会触发维度不匹配的赋值错误,根本无法完成操作。
额外逻辑错位:你给新列起的名字直接硬写为字符串"col_name_1",完全没有复用之前匹配到的列名结果,逻辑链路完全错位。 - 异常捕获逻辑错误
无差别的裸except:会把所有类型的异常(语法错、路径错、维度不匹配错)全部拦截,不做任何错误打印就直接返回None,让你完全感知不到哪一步抛出了异常,才会产生“赋值前流程都正常”的错觉。
修复方案
- 补全所有基础语法/API错误,把函数缺失的返回值逻辑加上
- 用具体的异常捕获代替裸except,打印具体报错信息,避免静默吞错导致定位困难
- 明确列赋值的业务规则:匹配到多列时需要指定整合逻辑(比如取第一个匹配列的值),不要直接把多列DataFrame往单列里塞
可直接运行的修复参考代码
import os import pandas as pd def read_csv_create_cols(id, year=2020): subs_2 = ["_rate"] # 修正路径拼接,用f-string替换变量 path = os.path.join(path1, f"{path2}/{id}/{year}") try: # 修正读CSV的API调用,补全语法 new_df = pd.read_csv(path, low_memory=False) new_df["id"] = id # 修正推导式的变量名错位问题 col_name_1 = [col for col in new_df.columns if "product" in col] col_name_2 = [col for col in new_df.columns if "date" in col] col_name_3 = [col for col in new_df.columns if all(sub in col for sub in subs_2)] # 修正赋值逻辑:匹配到目标列时取首个匹配列的值作为新列内容 if col_name_1: new_df["product_match_col"] = new_df[col_name_1[0]] if col_name_2: new_df["date_match_col"] = new_df[col_name_2[0]] if col_name_3: new_df["rate_match_col"] = new_df[col_name_3[0]] # 显式返回处理完成的DataFrame return new_df except Exception as e: # 打印具体报错,避免静默吞错 print(f"函数执行异常: {str(e)}") return None
内容的提问来源于stack exchange,提问作者user
相关产品推荐
相关产品推荐

