swift 条件函数 return
swift conditional function return
我想知道如何在 swift 中管理条件 return。例如,我 return 根据调用的 collectionview 委托创建一个自定义 UICollectionViewCell:
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {
if (collectionView.isEqual(collectionView1)) {
var cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell1", forIndexPath: indexPath) as Cell1
return cell
}
else if (collectionView.isEqual(collectionView2)) {
var cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell2", forIndexPath: indexPath) as Cell2
return cell
}
}
编译器说 "Missing return statement in a function expeted to return UICollectionViewCell",即使在这两种情况下我都在 returning 一个单元格。
我添加
解决了
return UICollectionViewCell()
在函数的底部,但我认为这不是正确的方法。
我知道我可以在第一个 'if' 上方声明单元格,修改它并在 'if' 之外的函数末尾 return,然后 [=29] =] 呼叫挂起。
谢谢大家
因为你需要 return 一个 UICollectionViewCell
,如果你为它创建一个单一的 var 和 return 它会更好(我不喜欢写多个return 方法中的语句)因此您可以将其更改为:
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell
{
var cell = UICollectionViewCell()
if (collectionView.isEqual(collectionView1))
{
cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell1", forIndexPath: indexPath) as Cell1
}
else if (collectionView.isEqual(collectionView2))
{
cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell2", forIndexPath: indexPath) as Cell2
}
return cell
}
为了解释@MidhunMP 的回答,现在您的代码可以在没有任何 return 值的情况下结束。例如,看看这段代码,它与您的相似:
func myFunc() -> Int {
let myNumber = random() % 3
if myNumber == 0 {
return 0
}
else if myNumber == 1 {
return 1
}
}
如果 myNumber
是 2 怎么办?函数结束时没有任何 return 值,这是不可能发生的。
要么将 return 语句移到代码末尾,要么添加一个 else
子句。两者都确保您的函数在任何情况下都会 return 一个值。
您将需要:
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {
var cell = UICollectionViewCell()
if (collectionView.isEqual(collectionView1)){
cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell1", forIndexPath: indexPath) as Cell1
} else if (collectionView.isEqual(collectionView2)){
cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell2", forIndexPath: indexPath) as Cell2
}
return cell
}
或者,
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {
var cell = UICollectionViewCell()
if (collectionView.isEqual(collectionView1)){
cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell1", forIndexPath: indexPath) as Cell1
return cell
} else if (collectionView.isEqual(collectionView2)){
cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell2", forIndexPath: indexPath) as Cell2
return cell
} else {
return cell;
}
}
不过,还是用第一个吧,因为它更优雅,也更容易理解它的意思。
编译器无法知道 collectionView
将永远是 collectionView1
或 collectionView2
在您的程序中,因此它会给出一条错误消息。
您可以做的是添加一个 else
案例来让编译器满意。
如果一切顺利,else
案例将永远不会被执行。如果有逻辑
你的程序出错,两个 if
条件不匹配,那么(在
"Debug" 配置)程序将中止并显示错误消息。
if (collectionView.isEqual(collectionView1)) {
let cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell1", forIndexPath: indexPath) as Cell1
// set cell properties ...
return cell
}
else if (collectionView.isEqual(collectionView2)) {
let cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell2", forIndexPath: indexPath) as Cell2
// set cell properties ...
return cell
}
else {
assertionFailure("unexpected collectionView")
return UICollectionViewCell()
}
或者(这只是前两个答案的微小变体),
将 cell
声明为 if
块之外的隐式解包选项:
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {
var cell : UICollectionViewCell!
if (collectionView.isEqual(collectionView1)){
cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell1", forIndexPath: indexPath) as Cell1
// set cell properties ...
} else if (collectionView.isEqual(collectionView2)){
cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell2", forIndexPath: indexPath) as Cell2
// set cell properties ...
}
return cell
}
如果 none 个条件匹配,则返回 nil
运行时异常。
首先,给大家回答,请不要使用var
。
其次,当然这是编译器方面的正确错误,因为委托方法不能确保 collectionView
是您定义的方法之一,并且要求您 return 是一个有效的单元格,所以如果您想要要在代码中明确保留这两种情况,那么您还需要定义一个有效但从未使用过的情况。
另请注意,将单元格转换为正确的 subclass 在这里是无用的,因为它们仍然被实例化为正确的 class 并且仍然 returned 作为 UICollectionViewCell
作为委托方法签名建议。
这是一个 Swifter 的实现方式:
/// define this in any .swift file included in your project
func ~=<T: AnyObject>(lhs: T, rhs: T) -> Bool {
return lhs === rhs
}
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {
let reuseIdentifier = cellReuseIdentifierForCollectionView(collectionView)
return epgCollectionView.dequeueReusableCellWithReuseIdentifier(reuseIdentifier, forIndexPath: indexPath)
}
private func cellReuseIdentifierForCollectionView(collectionView: UICollectionView) -> String {
switch collectionView {
case collectionView1:
return "Cell1"
case collectionView2:
return "Cell2"
default:
return "" // this never happens but is still a bit of a code smell
}
}
我找到解决办法了!比看起来更容易。只需将 "else if" 替换为 "else":
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {
if (collectionView.isEqual(collectionView1)) {
var cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell1", forIndexPath: indexPath) as Cell1
return cell
}
else (collectionView.isEqual(collectionView2)) {
var cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell2", forIndexPath: indexPath) as Cell2
return cell
}
}
现在可以了。谢谢大家!
我想知道如何在 swift 中管理条件 return。例如,我 return 根据调用的 collectionview 委托创建一个自定义 UICollectionViewCell:
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {
if (collectionView.isEqual(collectionView1)) {
var cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell1", forIndexPath: indexPath) as Cell1
return cell
}
else if (collectionView.isEqual(collectionView2)) {
var cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell2", forIndexPath: indexPath) as Cell2
return cell
}
}
编译器说 "Missing return statement in a function expeted to return UICollectionViewCell",即使在这两种情况下我都在 returning 一个单元格。
我添加
解决了return UICollectionViewCell()
在函数的底部,但我认为这不是正确的方法。
我知道我可以在第一个 'if' 上方声明单元格,修改它并在 'if' 之外的函数末尾 return,然后 [=29] =] 呼叫挂起。
谢谢大家
因为你需要 return 一个 UICollectionViewCell
,如果你为它创建一个单一的 var 和 return 它会更好(我不喜欢写多个return 方法中的语句)因此您可以将其更改为:
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell
{
var cell = UICollectionViewCell()
if (collectionView.isEqual(collectionView1))
{
cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell1", forIndexPath: indexPath) as Cell1
}
else if (collectionView.isEqual(collectionView2))
{
cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell2", forIndexPath: indexPath) as Cell2
}
return cell
}
为了解释@MidhunMP 的回答,现在您的代码可以在没有任何 return 值的情况下结束。例如,看看这段代码,它与您的相似:
func myFunc() -> Int {
let myNumber = random() % 3
if myNumber == 0 {
return 0
}
else if myNumber == 1 {
return 1
}
}
如果 myNumber
是 2 怎么办?函数结束时没有任何 return 值,这是不可能发生的。
要么将 return 语句移到代码末尾,要么添加一个 else
子句。两者都确保您的函数在任何情况下都会 return 一个值。
您将需要:
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {
var cell = UICollectionViewCell()
if (collectionView.isEqual(collectionView1)){
cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell1", forIndexPath: indexPath) as Cell1
} else if (collectionView.isEqual(collectionView2)){
cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell2", forIndexPath: indexPath) as Cell2
}
return cell
}
或者,
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {
var cell = UICollectionViewCell()
if (collectionView.isEqual(collectionView1)){
cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell1", forIndexPath: indexPath) as Cell1
return cell
} else if (collectionView.isEqual(collectionView2)){
cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell2", forIndexPath: indexPath) as Cell2
return cell
} else {
return cell;
}
}
不过,还是用第一个吧,因为它更优雅,也更容易理解它的意思。
编译器无法知道 collectionView
将永远是 collectionView1
或 collectionView2
在您的程序中,因此它会给出一条错误消息。
您可以做的是添加一个 else
案例来让编译器满意。
如果一切顺利,else
案例将永远不会被执行。如果有逻辑
你的程序出错,两个 if
条件不匹配,那么(在
"Debug" 配置)程序将中止并显示错误消息。
if (collectionView.isEqual(collectionView1)) {
let cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell1", forIndexPath: indexPath) as Cell1
// set cell properties ...
return cell
}
else if (collectionView.isEqual(collectionView2)) {
let cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell2", forIndexPath: indexPath) as Cell2
// set cell properties ...
return cell
}
else {
assertionFailure("unexpected collectionView")
return UICollectionViewCell()
}
或者(这只是前两个答案的微小变体),
将 cell
声明为 if
块之外的隐式解包选项:
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {
var cell : UICollectionViewCell!
if (collectionView.isEqual(collectionView1)){
cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell1", forIndexPath: indexPath) as Cell1
// set cell properties ...
} else if (collectionView.isEqual(collectionView2)){
cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell2", forIndexPath: indexPath) as Cell2
// set cell properties ...
}
return cell
}
如果 none 个条件匹配,则返回 nil
运行时异常。
首先,给大家回答,请不要使用var
。
其次,当然这是编译器方面的正确错误,因为委托方法不能确保 collectionView
是您定义的方法之一,并且要求您 return 是一个有效的单元格,所以如果您想要要在代码中明确保留这两种情况,那么您还需要定义一个有效但从未使用过的情况。
另请注意,将单元格转换为正确的 subclass 在这里是无用的,因为它们仍然被实例化为正确的 class 并且仍然 returned 作为 UICollectionViewCell
作为委托方法签名建议。
这是一个 Swifter 的实现方式:
/// define this in any .swift file included in your project
func ~=<T: AnyObject>(lhs: T, rhs: T) -> Bool {
return lhs === rhs
}
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {
let reuseIdentifier = cellReuseIdentifierForCollectionView(collectionView)
return epgCollectionView.dequeueReusableCellWithReuseIdentifier(reuseIdentifier, forIndexPath: indexPath)
}
private func cellReuseIdentifierForCollectionView(collectionView: UICollectionView) -> String {
switch collectionView {
case collectionView1:
return "Cell1"
case collectionView2:
return "Cell2"
default:
return "" // this never happens but is still a bit of a code smell
}
}
我找到解决办法了!比看起来更容易。只需将 "else if" 替换为 "else":
func collectionView(collectionView: UICollectionView, cellForItemAtIndexPath indexPath: NSIndexPath) -> UICollectionViewCell {
if (collectionView.isEqual(collectionView1)) {
var cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell1", forIndexPath: indexPath) as Cell1
return cell
}
else (collectionView.isEqual(collectionView2)) {
var cell = self.epgCollectionView.dequeueReusableCellWithReuseIdentifier("Cell2", forIndexPath: indexPath) as Cell2
return cell
}
}
现在可以了。谢谢大家!