2015-05-26 44 views
1

在数组扩展中创建通用函数时发现了这个隐晦的问题。比方说,我有用户类,我会用它来创建数组:在数组扩展中使用通用函数中的追加

class User : NSObject { 
    let name : String 
    let surname : String 

    init(name : String, surname : String) { 
     self.name = name 
     self.surname = surname 
    } 

    override var description : String { 
     return self.name + " " + self.surname 
    } 
} 

注意,我需要它是NSObject的子类。现在让我们创建两个用户并将其添加到用户数组中。

var user1 = User(name: "Jimmy", surname: "Page") 
var user2 = User(name: "David", surname: "Guilmour") 

var users = Array<User>() 
users.append(user1) 
users.append(user2) 

现在我需要数组扩展特定于阵列,或者用户的任何其他子类的功能,这将一些测试用户添加到用户的任何阵列。原因我写在扩展名,而不是我自己的类型,因为我想检查它的类型使用if let something = something as [User]。如果我建立自己的类型,我就无法做到这一点。

extension Array { 
    mutating func addTestUsers<T : User>() { 
     var testUser1 = User(name: "King", surname: "Brown") 
     var testUser2 = User(name: "Carlos", surname: "Santana") 
     self.append(testUser1) 
     self.append(testUser2) 
    } 
} 

问题来了,当使用追加函数或任何其他函数可以以某种方式改变初始数组。

错误:Cannot invoke append with argument list of type (User)

我知道这是因为扩展从未指定为用户的阵列的扩展,但我可以看到有没有办法,我可以做到这一点。

+2

您*不能*定义一个数组扩展方法,它只适用于数组的用户,请参阅http://stackoverflow.com/questions/24938948/array-extension-to-remove-object-by-value或http ://stackoverflow.com/questions/27350941/is-it-possible-to-make-an-array-extension-in-swift-that-is-restricted-to-one-cla。 –

回答

0

正如@马丁的r评论所说,如果你在Array extension to remove object by value一看,最高的投票答案提示写一个函数,它接受一个数组作为参数,你的情况,你可以这样做:

func addTestUsers(inout array: [User]) { 
    let user1 = User(name: "King", surname: "Brown") 
    let user2 = User(name: "Carlos", surname: "Santana") 
    array += [user1, user2] 
} 

然后,您可以使用此像这样:

var array = [User(name: "Jimmy", surname: "Page")] 
addTestUsers(&array) // [Jimmy Page, King Brown, Carlos Santana] 

如果您打算创建的User子类,但是,以前的方法是不合适的,因为你将无法通过子类的数组作为参数。在这种情况下,你可以重写addTestUsers接受你的子类,但一个更优雅的解决方案可能是:

func addTestUsers<T: User>(inout array: [T]) { 
    let user1 = T(name: "King", surname: "Brown") 
    let user2 = T(name: "Carlos", surname: "Santana") 
    array += [user1, user2] 
} 

对于以前功能工作,你需要在标记init(name : String, surname : String)Userrequired

class User : NSObject { 
    // ... 
    required init(name : String, surname : String) { 
     self.name = name 
     self.surname = surname 
    } 
    // ... 
} 

标记为required意味着User必须执行init(name : String, surname : String)的任何子类,因此可以安全使用T(name: "...", surname: "...")addTestUsers