- 原文リンク : Good Swift, Bad Swift — Part 2
- 原文著者 : Kristian Andersen
- 訳文出典 : 掘金翻訳計画
- 訳者 : Zheaoli
- 校正者: owenlyn, yifili09
不久之前,在我写的良い Swift、悪い Swift — パート 1一文中,我介绍了一些关于在 Swift 里怎样去写出优秀代码的小技巧。在 Swift 发布到现在的两年里,我花费了很长时间去牢牢掌握最佳的实践方法。欲知详情,请看这篇文章:良い Swift、悪い Swift — パート 1.
在这个系列的文章中,我将尝试提炼出我认为的 Swift 言語中良い部分と悪い部分。うーん、私も将来、優れた Swift が私を助けてくれることを望んでいます(うーん、君、見ないで、中央が君に決めたから、さあ、詩を二句読んでみて)。もし何か考えがあれば、または開発者としての人生経験を教えてくれたければ、Twitter で私に連絡してください。私のアカウントは ksmandersen です。
さて、無駄話はこれくらいにして、今日の授業を始めましょう。
guard
大法好、入 guard
保平安#
在 Swift 2.0 中, Swift 新增了一组让开发者有点陌生的特性。Guard
语句在进行防御性编程的时候将会起到不小的作用。(訳者注 1:防御的プログラミング(Defensive programming)は防御的設計の具体的な表れであり、プログラムの予期しない使用がプログラム機能に損害を与えないようにするためのものです。これは、ムルフィの法則の影響を減少または排除するための考え方と見なすことができます。防御的プログラミングは、悪用される可能性がある、いたずらや意図しない災害的影響を引き起こすプログラムに主に使用されます。出典はウィキペディア)。すべての Objective-C 開発者は防御的プログラミングに馴染みがあるかもしれません。この技術を使用することで、予期しない入力データを処理する際に、コードが異常を引き起こさないことを事前に確認できます。
Guard
语句允许你为接下来的代码设定一些条件和规则,当然你也必须钦定当这些条件(或规则)不被满足时要怎么处理。另外,guard
语句必须要返回一个值。在早期的 Swift 编程中,你可能会使用 if-else
语句来对这些情况进行预先处理。但是如果你使用 guard
语句的话,编译器会在你没有考虑到某些情况下时帮你对异常数据进行处理。
接下来的例子有点长,但是这是一个非常好的关于 guard
作用的实例。 didPressLogIn
函数在屏幕上的 button
被点击时被调用。我们期望这个函数被调用时,如果程序产生了额外的请求时,不会产生额外的日志。因此,我们需要提前对代码进行一些处理。然后我们需要对日志进行验证。如果这个日志不是我们所需要的,那么我们不再需要发送这段日志。但是更为重要的是,我们需要返回一段可执行语句来确保我们不会发送这段日志。guard
将会在我们忘记返回的时候抛出异常。
@objc func didPressLogIn(sender: AnyObject?) {
guard !isPerformingLogIn else { return }
isPerformingLogIn = true
let email = contentView.formView.emailField.text
let password = contentView.formView.passwordField.text
guard validateAndShowError(email, password: password) else {
isPerformingLogIn = false
return
}
sendLogInRequest(email, password: password)
}
当 let
和 guard
配合使用的时候将会有奇效。下面这个例子中,我们将把请求的结果绑定到一个变量 user
,之后通过 finishSignUp
方法函数使用 (这个变量)。如果 result.okValue
为空,那么 guard
将会产生作用,如果不为空的话,那么这个值将对 user
进行赋值。我们通过利用 where
来对 guard
进行限制。
currentRequest?.getValue { [weak self] result in
guard let user = result.okValue where result.errorValue == nil else {
self?.showRequestError(result.errorValue)
self?.isPerformingSignUp = false
return
}
self?.finishSignUp(user)
}
正直なところ、guard
は非常に強力です。うーん、もしまだ使っていないなら、真剣に考えるべきです。
subviews
を使用する際に、宣言と設定を同時に行う。#
前の一連の記事で述べたように、view
を開発する際、私はコード生成を好む傾向があります。view
の設定パターンに非常に慣れているため、レイアウトの問題や設定ミスが発生した場合、すぐにエラーの場所を特定できます。
開発中に、異なる設定プロセスを一緒にすることが非常に重要であることに気付きました。私の初期の Swift プログラミング経験では、通常 configureView
関数を宣言し、初期化時に設定プロセスをここに置いていました。しかし、Swift では プロパティ宣言コードブロック を利用して view
を設定できます(実際、これを何と呼ぶのかは分かりませんが(逃げ))。
うーん、以下の例では、2 つの subviews
、 bestTitleLabel
と otherTitleLabel
を含む AwesomeView
ビューがあります。2 つの subviews
は同じ場所で設定されています。設定プロセスは configureView
メソッドに統合されています。したがって、label
の textColor
プロパティを変更したい場合、どこを変更すればよいかはっきりと分かります。
class AwesomeView: GenericView {
let bestTitleLabel = UILabel().then {
$0.textAlignment = .Center
$0.textColor = .purpleColor()
}
let otherTitleLabel = UILabel().then {
$0.textAlignment = .Center
$0.textColor = .greenColor()
}
override func configureView() {
super.configureView()
addSubview(bestTitleLabel)
addSubview(otherTitleLabel)
// Configure constraints
}
}
上記のコードで、私があまり好きではないのは、label
を宣言する際に付随する型ラベルであり、その後コードブロック内で初期化して値を返すことです。Thenというライブラリを使用することで、少し改善できます。この小さな関数を利用して、プロジェクト内でコードブロックとオブジェクトの宣言を関連付けることができます。これにより、重複した宣言を減らすことができます。
class AwesomeView: GenericView {
let bestTitleLabel = UILabel().then {
$0.textAlignment = .Center
$0.textColor = .purpleColor()
}
let otherTitleLabel = UILabel().then {
$0.textAlignment = .Center
$0.textColor = .greenColor()
}
override func configureView() {
super.configureView()
addSubview(bestTitleLabel)
addSubview(otherTitleLabel)
// Configure constraints
}
}
異なるアクセスレベルを使用してクラスメンバーを分類する。#
うーん、私にとって最近起こった重要なことは、クラスと構造体のメンバーを結合するために特別な方法を利用したことです。これは、以前 Objective-C で開発していたときに身につけた習慣です。私は通常、プライベートメソッドを一番下に置き、公共および初期化メソッドを中間に置きます。そして、プロパティを公共プロパティからプライベートプロパティの順にコードの上部に配置します。うーん、以下の構造に従ってコードを整理できます。
- 公共プロパティ
- 内部プロパティ
- プライベートプロパティ
- 初期化コンテナ
- 公共メソッド
- 内部メソッド
- プライベートメソッド
静的 / クラスプロパティ / 定数の順に並べることもできます。人によっては、これに基づいていくつかの異なるものを追加するかもしれません。しかし、私にとっては、常に上記の方法でプログラミングを行っています。
さて、今回のエピソードはここまでです。もし良いアイデアや言いたいことがあれば、画面下部の連絡先を通じて私に連絡してください。もちろん、こんな方法でコインやバナナを投げて、私の文章をサポートし、購読することも歓迎します(大雲)。
次回予告:引き続き Swift のあれこれをお話ししますので、お見逃しなく、次回もお楽しみに。