10

いくつかの簡単な方法 (属性の削除、属性の追加、インデックスの削除) で既存の iPhone アプリのモデルを更新し、自動軽量移行を使用して永続ストアを移行できます。

データセットの典型的なサイズのため、処理時間は重要ではなく、ユーザーへのフィードバックを保証します。

NSMigrationManagermigrationProgress移行の実行時に KVO 通知を送信するシンプルで便利な値を提供します。これはフィードバックを提供するための基礎となりますが、推論されたモデル ( [NSMappingModel inferredMappingModelForSourceModel:destinationModel:error:]) を使用しようとすると、まったく同じデータセットに対して大幅に異なるタイミングが発生します。

オリジナルの iPhone (2G) でのプロファイル結果、キャッシュ サイズ: ディスク上で 1.785 MB。

自動推定軽量移行

PROFILE: CacheManager -migrateStore
PROFILE:   0.6130 (+0.6130) models loaded
PROFILE:   1.1759 (+0.5629) delegate -CacheManagerWillMigrate:
PROFILE:   1.2516 (+0.0757) persistent store coordinator loaded
PROFILE:   5.1436 (+3.8920) automatic lightweight migration completed
PROFILE:   5.5435 (+0.3999) delegate -CacheManagerDidFinishMigration:withError:

手動の推定移行

PROFILE: CacheManager -migrateStore
PROFILE:   0.6660 (+0.6660) models loaded
PROFILE:   1.1471 (+0.4811) inferred mapping model generated
PROFILE:   1.4046 (+0.2574) delegate -CacheManagerWillMigrate:
PROFILE:   1.5058 (+0.1013) persistent store coordinator loaded
PROFILE:   22.6952 (+21.1894) manual migration completed
PROFILE:   23.1478 (+0.4525) delegate -CacheManagerDidFinishMigration:withError:

したがって、推定モデルでは、手動の移行は自動の 5 倍以上の時間がかかります!


更新: モデルの読み込み

「移行オプション」のコアデータのドキュメントには、次のように記載されています。NSPersistentStoreCoordinator

NSInferMappingModelAutomaticallyOption

... マッピング モデルが見つからない場合、コーディネーターはマッピング モデルを推測しようとします。

そのため、XCode でビルド、コンパイル、およびバンドルされたマッピング モデルを削除 (または単に対象外) にして、推論された軽量の移行を実行できるようにする必要があります。


これは大きな矛盾であり、処理中の進行状況をまったく示さない軽量オプションです。NSPersistentStoreCoordinator -addPersistentStoreWithType:configuration:URL:options:error:

migrationProgress自動移行中に値を取得するサポートされている方法、または手動処理中に自動と同じくらい高速になるように推論されたマッピングモデルを構成する方法を誰かが提供できますか?


更新: バグレポート

WWDC のエンジニアに話を聞いたところ、migrationProgress軽量の自動移行処理を要求するバグ レポートを求められました。

進捗レポートを追加するために API が更新された場合は、もう一度更新します。

4

2 に答える 2

3

現在、Core Data はプライベート クラス を使用して、NSSQLiteInPlaceMigrationManager軽量の移行を実行しています。これは のサブクラスですNSMigrationManagerが、すべてを で処理しますmigrateStoreFromURL:type:options:withMappingModel:toDestinationURL:destinationType:destinationOptions:error:。一見すると、このクラスは実際には、手動で移行する必要があるようにすべてをメモリにプルするのではなく、SQLite ストアで直接変更を実行しています。

これは、軽量の移行がはるかに速く完了する理由を説明しています。

残念ながら、舞台裏で使用されているプラ​​イベート API に関するこの知識を使用したとしても、進行状況の表示を得るためにはあまり役に立ちません。の進行状況の値は現在変更されておらずNSSQLiteInPlaceMigrationManager、常にゼロです。の値currentEntityMappingもゼロのままのようです。

Apple が API を提供するまで、私たちは運が悪いようです。複製を開けられるようにレーダー番号を教えてください。

于 2012-03-15T16:21:16.313 に答える
2

推論されたモデルを使用する代わりに、マッピング モデルを自分で定義するとどうなりますか? 推論されたモデルの作成がパフォーマンス ヒットを引き起こしているように聞こえますが、マッピング モデルを直接定義してプロジェクトに含めることで解決します。

アップデート

私はすでにその戦略を試しましたが、XCode で生成されたマッピング モデルを使用すると、実行時に推定されるモデルとほぼ同じ処理時間が得られます。唯一の実際の違いは、バンドルからモデルをロードする時間が、実行時に推論するよりもわずかに速いことです。さらに、マッピング モデルがアプリにバンドルされると、自動移行は軽量ではなくなります。バンドルされたモデルを使用していると思われます。ターゲットからマッピング モデルを削除すると、automatic-lightweight の処理時間が最大 4 秒に戻ります

それは確かに直感に反しています。あなたのプロジェクトは、この非効率性の例として投稿するのに十分単純ですか? それとも、この問題を分離するテスト プロジェクトを持っていますか? どちらの状況でも、A) できれば謎を解決できるように、それを調べることは非常に役立ちます。または B) 逆は確かに当てはまるはずなので、かなり大きなバグとして Apple に報告します。

使用しているデータ セットの大きさは?

于 2010-03-29T05:35:08.907 に答える