CSV读取创建User对象时触发TypeError:int()参数不能为NoneType
Python读取CSV实例化对象报错排查与解决
问题背景
使用Python代码读取banking sytem/user.csv文件,将每行数据实例化为User类对象时,触发TypeError,错误信息:
TypeError: int() argument must be a string, a bytes-like object or a real number, not 'NoneType'
涉及代码如下:
import csv class User: #creates a user all = [] def __init__(self, name : str, lastname: str,password: str, password2: str, username: str, saldo: int): #assert saldo >= 0, "data is negatif that can't be right hu" self.name = name.capitalize() self.lastname = lastname.capitalize() self.saldo = saldo self.password = password self.password2 = password2 self.username = username User.all.append(self) @classmethod def instantiate_with_csv(cls): with open("banking sytem/user.csv",'r') as f: reader = csv.DictReader(f) items = list(reader) for item in items: User( name= str(item.get("name")), lastname=str(item.get("lastname")), password=str(item.get("password")), password2=str(item.get("password2")), username=str(item.get("username")), saldo=int(item.get('saldo')), ) User.instantiate_with_csv() print(User.all)
错误原因
错误出在saldo=int(item.get('saldo'))这一行:
item.get('saldo')返回了None,说明CSV文件中没有saldo这个表头字段,或者某一行的saldo字段为空/缺失。int()函数无法将None转为整数,因此触发TypeError。
解决方法
1. 校验CSV表头
先检查CSV文件的第一行(表头),确保存在saldo字段,且拼写、大小写和代码完全一致(比如CSV表头是Saldo而代码里写saldo会导致匹配失败)。
2. 容错处理缺失/空值
针对saldo字段的异常情况,有两种处理方式:
方式一:设置默认值
如果允许saldo为默认值(比如0),修改代码:
saldo=int(item.get('saldo', 0)) # 找不到saldo字段或值为空时,用0替代
方式二:跳过无效行
如果不希望创建saldo无效的用户,先判断再跳过:
saldo_str = item.get('saldo') # 跳过saldo缺失或为空的行 if saldo_str is None or not saldo_str.strip(): continue # 额外处理非整数的情况 try: saldo = int(saldo_str) except ValueError: continue
3. 优化其他字段的健壮性
其他字段用str(item.get("xxx"))会把None转为字符串"None",不符合实际需求,建议改为默认空字符串:
name= item.get("name", "").capitalize(), lastname=item.get("lastname", "").capitalize(),
修正后的完整代码
import csv class User: # 创建用户 all = [] def __init__(self, name : str, lastname: str,password: str, password2: str, username: str, saldo: int): # assert saldo >= 0, "余额不能为负数" self.name = name.capitalize() self.lastname = lastname.capitalize() self.saldo = saldo self.password = password self.password2 = password2 self.username = username User.all.append(self) @classmethod def instantiate_with_csv(cls): with open("banking sytem/user.csv",'r') as f: reader = csv.DictReader(f) items = list(reader) for item in items: # 处理saldo字段,避免None和非整数情况 saldo_str = item.get('saldo') if not saldo_str: continue try: saldo = int(saldo_str) except ValueError: continue User( name= item.get("name", ""), lastname= item.get("lastname", ""), password= item.get("password", ""), password2= item.get("password2", ""), username= item.get("username", ""), saldo= saldo, ) User.instantiate_with_csv() print(User.all)
内容的提问来源于stack exchange,提问作者Thomas Van Puyvelde
相关产品推荐
相关产品推荐

