[解決済み] Swift: print() vs println() vs NSLog()
質問
とはどう違うのですか?
print
,
NSLog
と
println
また、それぞれどのような場合に使用すればよいのでしょうか?
例えば、Pythonで辞書を表示させたい場合、次のようにします。
print myDict
しかし、今は他に2つのオプションがあります。それぞれをいつ、どのように使えばいいのでしょうか?
どのように解決するのですか?
いくつかの違い
-
print
対println
:は
print
関数は、アプリをデバッグする際にXcodeコンソールにメッセージを表示します。この
println
は、Swift 2 で削除されたこのバリエーションで、もう使用されることはありません。を使っている古いコードを見かけたらprintln
に置き換えてください。print
.Swift 1.xに戻りました。
print
は出力される文字列の末尾に改行文字を追加しませんでしたがprintln
があります。しかし、今となってはprint
は常に文字列の末尾に改行文字を追加しますが、そうさせたくない場合は、文字列の末尾にterminator
のパラメータは""
. -
NSLog
:-
NSLog
は出力にタイムスタンプと識別子を追加するのに対してprint
はしません。 -
NSLog
ステートメントはデバイスのコンソールとデバッガのコンソールの両方に表示されるのに対しprint
はデバッガコンソールにのみ表示されます。 -
NSLog
iOS 10-13/macOS 10.12-10.xではprintf
-スタイルのフォーマット文字列です。NSLog("%0.4f", CGFloat.pi)
を生成することになります。
2017-06-09 11:57:55.642328-0700 MyApp[28937:1751492] 3.1416
-
NSLog
は、iOS 14/macOS 11から文字列補間を使用することができます。(それから、やはりiOS 14とmacOS 11では、一般的にLogger
オーバーNSLog
. 次点参照)
現在では、一方
NSLog
はまだ機能しますが、一般的には、「ユニファイドロギング」(後述)を使うことになるでしょう。NSLog
. -
-
iOS 14/macOS 11で有効なのは
Logger
インターフェイスを「ユニファイドロギング」方式に変更しました。への導入はLogger
は、WWDC2020をご覧ください。 Swiftでロジスティクスを探求する .-
使用するには
Logger
をインポートする必要があります。os
:import os
-
好きなもの
NSLog
また、ユニファイドロギングでは、Xcodeデバッグコンソールとデバイスコンソールの両方にメッセージが出力されます。 -
を作成します。
Logger
とlog
にメッセージを送る。let logger = Logger(subsystem: Bundle.main.bundleIdentifier!, category: "network") logger.log("url = \(url)")
外部のConsoleアプリからアプリを観察する場合、フィルタリングのために
subsystem
とcategory
. デバッグメッセージを、(a) アプリに代わって他のサブシステムが生成したメッセージ、または (b) 他のカテゴリやタイプのメッセージと区別することは非常に便利です。 -
ロギングメッセージには、次のような異なるタイプを指定することができます。
.info
,.debug
,.error
,.fault
,.critical
,.notice
,.trace
など。logger.error("web service did not respond \(error.localizedDescription)")
そのため、外部のコンソールアプリを使用する場合、特定のカテゴリのメッセージのみを表示するように選択できます(例えば、コンソールの「アクション」メニューで「デバッグメッセージを含める」を選択すると、デバッグメッセージのみを表示するようにできます)。これらの設定は、ディスクにログを記録するかどうかなど、多くの微妙な問題の詳細も決定します。詳しくはWWDCのビデオをご覧ください。
-
デフォルトでは、数値以外のデータはログで冗長化されます。URLを記録した例では、アプリがデバイス本体から起動され、macOSコンソールアプリから見ていた場合、macOSコンソールで以下のように表示されます。
url = <private>
このメッセージにユーザーの機密データが含まれないと確信していて、macOSのコンソールで文字列を見たい場合は、そうするしかないでしょう。
os_log("url = \(url, privacy: .public)")
-
-
iOS 14/macOS 11に先立ち、iOS 10/macOS 10.12で導入されたのは
os_log
を「ユニファイドロギング」に変更しました。ユニファイドロギング全般の紹介は、WWDC2016の動画をご覧ください。 ユニファイドロギングとアクティビティトレース .-
インポート
os.log
:import os.log
-
を定義する必要があります。
subsystem
とcategory
:let log = OSLog(subsystem: Bundle.main.bundleIdentifier!, category: "network")
を使用する場合
os_log
の場合、文字列の補間ではなく、printf形式のパターンを使用します。os_log("url = %@", log: log, url.absoluteString)
-
ログメッセージの種類は、以下のいずれかを指定することができます。
.info
,.debug
,.error
,.fault
(または.default
):os_log("web service did not respond", type: .error)
-
を使用する場合、文字列補間を使用することはできません。
os_log
. 例えばprint
とLogger
するんですね。logger.log("url = \(url)")
しかし
os_log
をしなければならないでしょう。os_log("url = %@", url.absoluteString)
-
は
os_log
は同じデータプライバシーを強制しますが、 printf フォーマッタで公開の可視性を指定します (たとえば%{public}@
よりも%@
). 例:外部機器から見たい場合は、そうする必要がある。os_log("url = %{public}@", url.absoluteString)
-
また、Instrumentsの活動範囲を見たい場合は、「Points of Interest」ログを使用することができます。
let pointsOfInterest = OSLog(subsystem: Bundle.main.bundleIdentifier!, category: .pointsOfInterest)
と範囲を開始します。
os_signpost(.begin, log: pointsOfInterest, name: "Network request")
で終わらせてください。
os_signpost(.end, log: pointsOfInterest, name: "Network request")
-
結論から言うと
print
は、Xcodeでの単純なロギングには十分ですが、統一されたロギング(
Logger
または
os_log
) は、同じことを実現しますが、はるかに大きな機能を提供します。
ユニファイドロギングの威力は、Xcodeの外でテストする必要があるiOSアプリをデバッグするときに、顕著に現れます。例えば、バックグラウンドフェッチのようなバックグラウンドのiOSアプリのプロセスをテストするとき、Xcodeデバッガに接続されていると アプリのライフサイクルを変更する . そのため、Xcodeのデバッガからアプリを起動するのではなく、デバイス自体からアプリを実行して、物理的なデバイス上でテストしたいことが頻繁にあります。Unified Loggingを使えば、iOSデバイスのログステートメントをmacOSのコンソールアプリから見ることができます。
関連
-
[解決済み] ファイルにログを記録し、標準出力に印刷するためのロガー設定
-
[解決済み] Swiftのstatic funcとclass funcの違いは何ですか?
-
[解決済み] Swift言語におけるエクスクラメーションマークの意味とは?
-
[解決済み] SwiftはPass By ValueかPass By Referenceか
-
[解決済み] 文字列フォーマット:% vs. .format vs. f-stringリテラル
-
[解決済み] Swiftで#pragmaマーク?
-
[解決済み] Swift Betaのパフォーマンス:配列のソート
-
[解決済み] C#のWindowsコンソールアプリで現在行を更新するにはどうしたらいいですか?
-
[解決済み] SwiftでUIAlertViewを作成するにはどうしたらいいですか?
-
[解決済み】Swiftで2つのDate(月/日/時間/分/秒)の差を取得する。
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
[解決済み] これを解決するにはどうしたらいいのでしょうか。UILabel.textは、メインスレッドからのみ使用する必要があります。
-
[解決済み] Swiftでbase64StringをStringに変換する方法とは?
-
[解決済み] メインスレッドチェッカー バックグラウンドスレッドで呼び出された UI API: -[UIApplication applicationState].
-
[解決済み] Swiftベースのアプリケーションは、OS X 10.9/iOS 7以下でも動作しますか?
-
[解決済み] 純粋な」Swift で弱いプロトコル参照を作るには (@objc なしで) どうしたらいいですか?
-
[解決済み] Swiftでdispatch_onceのシングルトンモデルを使う
-
[解決済み】iOSシミュレーターのコンソールログを取得する方法を教えてください。
-
[解決済み】Swiftの構造体のために、メンバーごとの初期化子をデフォルトで公開するにはどうすればよいですか?
-
[解決済み】Swiftで弱参照の配列を宣言するには?
-
[解決済み] プッシュ通知からアプリが起動/開封されたかどうかを検出する