私の友人はNSDictionaryと何か変わった動作を発見しました。なぜそれが起こるのか不思議です。次のコードを考えてみましょう:このObjective Cコールがハングアップしているように見えるのはなぜですか?
NSDictionary *dict = [[NSDictionary alloc] init];
// Oops, we can't mutate an NSDictionary
[dict setObject:[[NSNull alloc] init] forKey:@"test"];
NSLog(@"Set");
コードは「『NSDictionaryのは、』 『:forKey:のsetObject』に応答しないこと」というコンパイル時に警告を生成します。それはすべてが順調と良いことだ、とあなたはとにかくそれを実行する場合は、コンソールでこの出力を取得します:
- [__ NSCFDictionaryのsetObject:forKey:]:不変オブジェクトに送られた変異法
もう一度、あなたは何が起こると思いますか。しかし、現時点ではのアプリケーションは、キャッチされない例外のためにをクラッシュせず、終了しません。 setObject:forKey:メソッドは単に返されず、アプリケーションはハングしているように見えます。次のNSLog
は決して実行されません。 GDBを使用してメソッドをステップインしたり、メソッドに入れようとすると、デバッグは終了するようですが、明示的なエラーメッセージは表示されません。アプリケーションは引き続き実行されますが、デバッガは実行中のコードがどこに「スタックしている」かのヒントを提供しません。
ここでは何が起こっていますか?この場合、アプリは実際に何をしていますか?なぜ、NSInternalInconsistencyExceptionやそのようなものでクラッシュしないのですか?
編集は:求めている人のために、私は、OS Xのライオン(10.7.2)にXCodeの4.1を実行していると建物 "のApple LLVMコンパイラ2.1。"私はあなたがXCode 4で新しいCocoaプロジェクトを使うときのデフォルト設定をすべて使用しています。私はプログラムをデバッグするかどうかに関係なく、同じ非クラッシュ動作を経験します。デバッグビルディングからリリースビルディングに変更することで違いはありません。私はFinderで.appファイルを手動で見つけて、それをダブルクリックしてXCodeの外で実行することさえできますが、それでもクラッシュはありません。
デバッガでは実行しないでください。私はそれがハードクラッシュ賭ける。私は、デバッガ環境は、特に例外の周りの実行時環境にいくつかの予期しない影響を与えることができ、それらをヒットしたときに何が起こるかを見つける。 –
例外がスローされると、例外の後に次の行ではなく、例外をキャッチして制御が再開されます。あなたの例では、デバッガまたはランタイムのいずれかの腸が例外を "捕まえ"ました。いずれにしても、-setObject:forKey:が例外をスローした後にNSLogが発生することは期待できません。 –
@VincentGable:プログラムがクラッシュしたら同意しました。私はNSLogが呼び出されなかったことに少しも驚かないでしょう。私が驚いたことは、それがクラッシュしたり次の行に進むことがないことです。それは、どちらか一方をすべきだと思われます。質問した人には、私が実行している環境に関するいくつかの追加の詳細を質問に更新しました。 –