我在NSURL上写了以下类扩展:
extension NSURL
{
var linkComponents: LinkComponents
{
var pathComponents = self.pathComponents ?? []
if let first = pathComponents.first where first == "/"
{
pathComponents.removeFirst()
}
return LinkComponents(components: pathComponents)
}
var linkPath: String
{
return self.path ?? ""
}
}
它包含一个计算(get-only)属性:
var linkComponents: LinkComponents
当我尝试在单元测试目标中测试此计算属性时,编译器会抛出错误并说出Ambiguous use of 'linkComponents'
并建议一些“候选”。
这似乎是一个访问控制问题。我的测试文件中的import语句具有@testable
注释。所有我的其他测试(对于非计算属性)编译a-ok,而不必指定超出默认internal
的任何访问控制。如果我将这个特定的计算属性转换为函数,则测试目标编译为a-ok。
是否可以在Swift中对计算属性进行单元测试?如果是这样,怎么样?不用说(1)我不想将这个计算属性转换为函数,(2)我不想将public
添加到所有内容中。
修改1
编译器建议的“候选人”实际上只是一个“候选人”而且它是我的计算属性。即编译器正确识别计算属性,但它不会正式将其识别为唯一有效的候选者。
修改2
实际上,将其转换为函数也不起作用。鉴于我正在我编写的类的扩展中测试函数。也许这与测试Foundation类扩展中的函数有关(如本例中的NSURL)。
编辑3
进一步调查之后看起来这是由于LinkComponents
计算属性的返回类型(linkComponents
)。编译器不喜欢这个。如果我将返回类型更改为String
,那就可以了。如果我在测试用例本身或计算属性的主体中引用类型为LinkComponents
的对象,那么它也是一个好的。只有当编译器抱怨的计算属性的类型为LinkComponents
时才会这样。这是LinkComponents
:
enum LinkComponents
{
case None
case Any(String, String?, String?, String?, String?)
init(components: [String])
{
switch components.count
{
case 0:
self = .None
case 1:
self = .Any(components[0], nil, nil, nil, nil)
case 2:
self = .Any(components[0], components[1], nil, nil, nil)
case 3:
self = .Any(components[0], components[1], components[2], nil, nil)
case 4:
self = .Any(components[0], components[1], components[2], components[3], nil)
case 5:
self = .Any(components[0], components[1], components[2], components[3], components[4])
default:
self = .Any(components[0], components[1], components[2], components[3], components[4])
}
}
}