【Swift】Core Dataの使い方。フェッチリクエストで取得するデータを絞り込む(Swift 2.1、XCode 7.2)

2020年6月16日

NSFetchRequestとは

本記事では、Core Dataの機能のNSFetchRequest(以下、フェッチリクエスト)について説明する。

フェッチリクエストとは、Core Dataを使って保存したデータをメモリ上に展開することを要求する機能である。

フェッチリクエスト

 

過去の記事でも何回もフェッチリクエストをしてきた。そのときは特定のエンティテイのデータを丸ごと取得したが、フェッチリクエストに絞り込み条件を付けると、条件に適合するデータのみを取得できる。

フェッチリクエストに絞り込み条件を付けるには、以下のコードのようにフェッチリクエストのpredicateプロパティに値を設定する。以下コードの「name = '広島’」は、属性nameの値が広島であるデータのみを取得するということだ。

 

絞り込み条件を試す

絞り込み条件を付けたフェッチリクエストを試してみよう。

検証に使ったXCodeのプロジェクトをGitHubに置いたので試してみる人はご利用されたし。
⇒「テスト用プロジェクト

Search Barに入力した文字列で保存データを検索し、検索結果をテーブルビューに表示するものを実装しておいた。何も入力しなかった場合は全データが表示される。

 

以下はViewControllerのコード。フェッチリクエストの条件式(青色網掛け箇所)を変更しながら検証を行った。

 

以下にフェッチ要求のフォーマットに指定できるものをまとめる。ただし、フェッチ要求の仕様はとても広いので使われそうなものに絞って掲載している。

詳細を知りたいかたは以下の公式ドキュメントを参照されたし。
⇒「Predicate Programing Guide
⇒「Predicate Programing Guide(日本語)
⇒「Core Data Programing Guide(日本語)

 

プレースホルダー

プレースホルダーとは、プログラミング実行時に文字列を完成させるための、文字列中の仮置きの値ことである。例えば、「こんにちは、◯さん」の◯をプログラミング実行時に埋めるイメージ。

ホルダー 説明
%@ 文字列、日時などを埋め込む
NSPredicate(format:"name = %@", "テスト")
%K プロパティを埋め込む
NSPredicate(format:"%K => 280", "price")
%D、%d、%i 整数を埋め込む
NSPredicate(format:"price => %D", 280)
%f 不動小数を埋め込む
NSPredicate(format:"approvalRate => %f", 25.0)

 

数値、日付を比較する

いつも使っている比較演算子をフォーマットでも使用できる。

演算子 説明
=、== 右と等しい
NSPredicate(format:"price = %D", 280
!=、<> 右と等しくない
NSPredicate(format:"price != %D", 280
< 右より小さい
NSPredicate(format:"price < %D", 200)
> 右より大きい
NSPredicate(format:"price > %D", 200)
<=、=< 右以下
NSPredicate(format:"price <= %D", 300)
>=、=> 右以上
NSPredicate(format:"price >= %D", 300)
BETWEEN 右の2つの値の間
NSPredicate(format:"price BETWEEN {%D, %D}", 200, 300)
IN 右のどれかと一致する
NSPredicate(format:"price IN {%D, %D, %D}", 280, 300, 420

 

数字に限らず日付も比較することができる。やってみよう。

ViewController.swiftの本を検索する箇所を以下のコードに変更する。

 

以下は実際のプレイ動画。指定した日付以降に出版された雑誌が検索された。

文字列を比較する

演算子 説明
=、== 右と等しい
NSPredicate(format:"name == %@","週刊少年ジャンプ")
!=、<> 右と等しくない
NSPredicate(format:"name != %@","週刊少年ジャンプ")
CONTAINS 右の文字列が含まれる
NSPredicate(format:"name CONTAINS %@","少年")
LIKE 右の文字列パターンが含まれる
NSPredicate(format:"name LIKE %@","?刊少年*")
BEGINSWITH 右の文字列で始まる
NSPredicate(format:"name BEGINSWITH %@","週刊")
ENDSWITH 右の文字列で終わる
NSPredicate(format:"name ENDSWITH %@","ジャンプ")
IN 右のリストのどれかと一致する
NSPredicate(format:"name IN {%@, %@}" , "週刊少年ジャンプ", "最強ジャンプ")
MATCHES 右の正規表現に当てはまる
NSPredicate(format:"name MATCHES %@", "[週刊|月刊].*")

 

条件と一致しないものを取得するには、条件式の頭に「NOT」か「!(ビックリマーク)」をつける。

 

文字列の比較ではcまたはdのオプションをつけれる。

cは「大文字小文字の区別をしない」dは「発音記号の有無は同一の文字として扱う(例、ä, ö, ü)」

 

複数の条件を組み合わせる

「かつ」、「または」を使って条件を組み合わせられる。

演算子 説明
AND、&& 左の条件式 かつ 右の条件式
NSPredicate(format:"name CONTAINS %@ AND price > %d", "週刊", 280)
OR、|| 左の条件式 または 右の条件式
NSPredicate(format:"name CONTAINS %@ || price > %d", "週刊", 400)

 

条件を増やして複雑になってきたら括弧を使って条件の範囲を分かりやすくすべし。

 

集計結果を利用する

最大値、最小値、平均などの集計結果を条件に利用できる。

演算子 true条件 使用例
@avg 平均 NSPredicate(format:"price > @avg.price")
@max 最大値 NSPredicate(format:"price = @max.price")
@min 最小値 NSPredicate(format:"price = @min.price")
@sum 合計
@count 件数