构建PyTorch Dataset类时迭代出现'tuple' object has no attribute 'iloc'错误排查——BERT问答模型BioQA数据集开发问题
问题分析与修复方案
你遇到的 AttributeError: 'tuple' object has no attribute 'iloc' 是代码里几个容易忽略的小错误导致的,我帮你逐一排查并修复:
1. __init__ 方法中多余的逗号导致变量变成元组
看你的类初始化函数:
def __init__(self, data:pd.DataFrame, tokenizer: T5Tokenizer,source_max_token_len:int = 512, target_max_token_len: int = 32): self.data = data, # 这里的逗号是致命错误! self.tokenizer = tokenizer, # 还有这里的逗号 self.source_max_token_len = source_max_token_len, # 以及这里的逗号 self.target_max_token_len = target_max_token_len
在Python里,变量赋值后加逗号会自动把它变成单元素元组,比如 self.data = data, 会让原本的DataFrame变成 (dataframe,) 这样的元组结构。元组自然没有 iloc 方法,这就是报错的直接原因。
解决方法:把这三行后面的逗号全部删掉。
2. __getitem__ 里的未定义变量与未调用实例属性
- 你直接用了
tokenizer,但它是类的实例属性,应该写成self.tokenizer - 代码里出现的
sample_question完全没有定义,应该替换成你已经获取到的data_row(这明显是复制粘贴时的失误)
3. 修正后的完整代码
class BioQADataSet(Dataset): def __init__(self, data:pd.DataFrame, tokenizer: T5Tokenizer, source_max_token_len:int = 512, target_max_token_len: int = 32): # 移除所有多余的逗号,确保变量类型正确 self.data = data self.tokenizer = tokenizer self.source_max_token_len = source_max_token_len self.target_max_token_len = target_max_token_len def __len__(self): return len(self.data) def __getitem__(self, index: int): data_row = self.data.iloc[index] # 使用self.tokenizer,并用data_row替代未定义的sample_question source_encoding = self.tokenizer( data_row['question'], data_row["context"], max_length = self.source_max_token_len, padding = 'max_length', truncation = "only_second", return_attention_mask = True, add_special_tokens = True, return_tensors = 'pt' ) target_encoding = self.tokenizer( data_row['answer_text'], max_length = self.target_max_token_len, padding = 'max_length', truncation = True, return_attention_mask = True, add_special_tokens = True, return_tensors = 'pt' ) labels = target_encoding["input_ids"] labels[labels==0]= -100 return dict( question = data_row["question"], context = data_row['context'], answer = data_row['answer_text'], input_ids = source_encoding["input_ids"].flatten(), attention_mask = source_encoding['attention_mask'].flatten(), labels = labels.flatten() )
现在再运行你的遍历代码:
for data in sample_dataset: print(data) break
应该就能正常输出数据行,不会再触发 AttributeError 了。
内容的提问来源于stack exchange,提问作者Ranit
相关产品推荐
相关产品推荐

