可以将文章内容翻译成中文,广告屏蔽插件可能会导致该功能失效(如失效,请关闭广告屏蔽插件后再试):
问题:
I have a Human class with a function that takes any amount of people and determines if someone is older than any of those people, then returns an array with the people he/she is older than.
func isOlderThan(people: Human...) -> [Human] { var p: [Human] for person in people { if age > person.age { p.append(person) } } return p }
However at
p.append(person)
I'm getting the error
Variable p passed by reference before being initialized
Anyone sure why this is? Thanks!
回答1:
Your declaration of p is just that, a declaration. You haven't initialised it. You need to change it to
var p = [Human]()
Or, as @MartinR points out,
var p: [Human] = []
There are other equivalent constructs, too, but the important thing is you have to assign something to the declared variable (in both cases here, an empty array that will accept Human
members).
Update For completeness, you could also use:
var p: Array<Human> = []
or
var p = Array<Human>()
回答2:
You are better off simply using the filter
method:
func isOlderThan(people: Human...) -> [Human] { return people.filter { self.age > $0.age } }
It works like this:
20> class Human { 21. let age : Int 22. init (age: Int) { self.age = age } 23. func isOlderThan (people: Human...) -> [Human] { 24. return people.filter { self.age > $0.age } 25. } 26. } 28> let me = Human(age:27) me: Human = { age = 27 } 29> me.isOlderThan (Human(age:25), Human(age:30)) $R10: [Human] = 1 value { [0] = { age = 25 } }
By the way, before long you'll find it useful to define an additional method specified as:
func isOlderThan(people: [Human]) -> [Human] { ... }
because as soon as you have an array and since there is no apply
method yet in Swift, your original method won't work.
回答3:
append
is a mutating
method of the struct Array
.
You can think of a struct method as a function with a hidden self
parameter. By default, parameters to functions are constants, and therefore you cannot do anything to it that you cannot do to a constant. A mutating
struct method needs to do things that cannot be done to a constant, therefore, it must take the self
parameter as inout
, i.e. as if it's passed by reference. Thus, you can only call a mutating method on something you can pass by reference. And you cannot pass an uninitialized variable by reference.