问题分析描述:
我是在使用robustbench时出现了这个问题,问题出现在robustbench的源代码中,因此要修改相应库的代码。
TypeError 表示你试图使用 ‘/’ 操作符的对象的类型有问题。这里使用 ‘/’ 操作符来连接路径,data_dir 是一个 PosixPath 对象,但似乎 CORRUPTIONS_DIR_NAMES[dataset] 是一个字典对象,因此出现了错误。
这个问题很可能是 dataset 不是 CORRUPTIONS_DIR_NAMES 字典的正确键,或者 CORRUPTIONS_DIR_NAMES 的定义不正确。变量 dataset 应该是 CORRUPTIONS_DIR_NAMES 字典的一个键,但该字典没有一个与 dataset 的值匹配的键。
因此必须调试 CORRUPTIONS_DIR_NAMES 和 dataset 以确保它们被正确定义和使用。CORRUPTIONS_DIR_NAMES 应该是一个字典,其中的键是BenchmarkDataset的值,值是字符串目录名。这里,数据集被作为BenchmarkDataset.cifar_10从load_cifar10c传到load_corruptions_cifar。
检查CORRUPTIONS_DIR_NAMES字典的内容,验证它是否包含BenchmarkDataset.cifar_10这个键。例如,如果 CORRUPTIONS_DIR_NAMES 被期望有 BenchmarkDataset 类型的键,它应该看起来像这样:
CORRUPTIONS_DIR_NAMES = {
BenchmarkDataset.cifar_10: ‘dir_name_for_cifar_10’,
BenchmarkDataset.cifar_100: ‘dir_name_for_cifar_100’,
# …other datasets…
}
问题排查:
在 Jupyter notebook 中检查 CORRUPTIONS_DIR_NAMES
字典的内容非常简单。你只需要在一个新的单元格中打印这个字典就可以了。请按照以下步骤操作:
-
在 Jupyter notebook 中创建一个新的代码单元格。你可以通过点击 “Insert” -> “Insert Cell Below” 来创建一个新的单元格。
-
在新的单元格中,输入以下代码:
pythonCopy code
print(CORRUPTIONS_DIR_NAMES)
-
点击 “Run” 或者使用快捷键 “Shift+Enter” 来运行这个单元格。
这会打印出 CORRUPTIONS_DIR_NAMES
字典的内容,让你能够查看字典中的所有键值对。这样你就能检查 BenchmarkDataset.cifar_10
是否存在于字典中,以及它对应的值是什么。
如果你的代码中没有直接导入或定义 CORRUPTIONS_DIR_NAMES
,那么你可能需要在 print
语句前加上正确的模块或包的名称。例如,如果 CORRUPTIONS_DIR_NAMES
在 robustbench.data
模块中定义,你应该这样打印它:
pythonCopy code
print(robustbench.data.CORRUPTIONS_DIR_NAMES)
这样你就能看到 CORRUPTIONS_DIR_NAMES
字典的内容了。
问题解决
经检查字典内容没有问题:CORRUPTIONS_DIR_NAMES是一个嵌套的字典,其中键是BenchmarkDataset枚举,值本身是另一个字典,键是ThreatModel枚举,值是相应的目录名称。
然而,在robustbench的代码中,把CORRUPTIONS_DIR_NAMES当作一个字典,BenchmarkDataset枚举是键,字符串是值,这导致了TypeError。需要考虑到字典的嵌套结构。
你应该修改发生错误的那行代码,以正确处理嵌套的字典:
data_root_dir = data_dir / CORRUPTIONS_DIR_NAMES[dataset][ThreatModel.corruptions]
在修改后的代码中,CORRUPTIONS_DIR_NAMES[dataset][ThreatModel.corruptions]正确提取了BenchmarkDataset.cifar_10数据集和ThreatModel.corrupts威胁模型对应的目录名称。如果你还没有这样做,你需要导入ThreatModel枚举。