コレクションを使用した作業
ここでは、InterSystems IRIS® データ・プラットフォームにおいてコレクション API (リストおよび配列) を使用する方法について説明します。コレクションは、オブジェクトのプロパティとして使用することも、スタンドアロンで使用することもできます。
コレクションの概要
コレクションは、同じタイプの要素が複数含まれるオブジェクト・クラスです。これらのタイプとしては、文字列や整数などのリテラル値、またはオブジェクトがあります。コレクション内の各要素は、キー (コレクション内でのその要素の位置) と値 (その位置に格納されるデータ) で構成されます。コレクションのメソッドとプロパティを使用して、以下のようなアクションを実行できます。
-
キーに基づいて要素にアクセスし、値を変更する。
-
指定したキー位置に要素を挿入または削除する。
-
コレクション内の要素の数を数える。
InterSystems IRIS® データ・プラットフォームには、リストと配列という 2 種類のコレクションの API が用意されています。
-
リスト・コレクションでは、要素は順番に並べられます。リスト内のキーは、1 から N の整数で、N はリスト内の最後の要素です。以下の例では、リストの 2 番目の要素 (つまり、キーが 2 の要素) を文字列値 red に設定します。
do myList.SetAt("red",2)
-
配列コレクションでは、要素の作成時に指定した任意のキー名に基づいて、要素にアクセスします。文字列または数値のキー名を指定できます。以下の例では、配列の color キーを文字列値 red に設定します。
do myArray.SetAt("red","color")
配列内の要素は、キーの順に並べられます。最初は数値キーで、小さい数値から大きい数値の順に並べられ、次に文字列キーで、アルファベット順に大文字の後に小文字という順に並べられます。例 : -2、-1、0、1、2、A、AA、AB、a、aa、ab。
コレクション・プロパティの定義
リストまたは配列のプロパティを定義するには、以下のプロパティ定義構文を使用します。
Property MyProp as list of Type;
Property MyProp as array of Type;
MyProp はプロパティ名です。Type は、データ型クラスまたはオブジェクト・クラスのどちらかです。
以下の例は、%StringOpens in a new tab 値のリストのプロパティを定義する方法を示しています。
Property Colors as list of %String;
以下のコードは、Doctor オブジェクトの配列のプロパティを定義する方法を示しています。
Property Doctors as array of Doctor;
InterSystems IRIS では、コレクション・プロパティを %Collection パッケージ内にクラスのインスタンスとして格納します。これらのクラスには、コレクションの操作に使用できるメソッドとプロパティが含まれます。
以下の表は、コレクション・プロパティの定義方法と、その格納に使用する %Collection クラスの概要です。
コレクション・タイプ | %Collection クラス |
---|---|
文字列、整数、または他のデータ型のリスト |
%Collection.ListOfDTOpens in a new tab |
オブジェクトのリスト |
%Collection.ListOfObjOpens in a new tab |
文字列、整数、または他のデータ型の配列 |
%Collection.ArrayOfDTOpens in a new tab |
オブジェクトの配列 |
%Collection.ArrayOfObjOpens in a new tab |
プロパティのタイプとして %Collection クラスを直接使用しないでください。例えば、以下のようなプロパティ定義を作成してはいけません。
Property MyProp as %Collection.ArrayOfDT;
スタンドアロン・コレクションの定義
コレクション・プロパティを定義する別の方法として、メソッドの引数や戻り値として使用するためにスタンドアロン・コレクションを定義できます。スタンドアロン・コレクションを定義するために、InterSystems IRIS® データ・プラットフォームでは、%Library パッケージに、コレクション・プロパティの格納に使用する %Collection クラスと同様の機能を提供するクラスが用意されています。
スタンドアロン・コレクションを作成するには、適切なクラスの %New() メソッドを呼び出し、そのクラスのインスタンスを取得します。次に、そのインスタンスのメソッドを使用して、コレクションの操作を実行します。例えば、以下のコードは、%Library.ListOfDataTypesOpens in a new tab クラスを使用して文字列のリストを作成し、3 つの要素をリストに挿入してから、リスト内の要素の数を表示します。
set mylist=##class(%ListOfDataTypes).%New()
do mylist.Insert("red")
do mylist.Insert("green")
do mylist.Insert("blue")
write mylist.Count()
以下の表は、スタンドアロン・コレクションの定義方法と、その作成に使用する %Library クラスの概要です。
コレクション・タイプ | %Library クラス | 作成構文の例 |
---|---|---|
文字列、整数、または他のデータ型のリスト |
%ListOfDataTypesOpens in a new tab |
set myList = ##class(%ListOfDataTypes).%New() |
オブジェクトのリスト |
%ListOfObjectsOpens in a new tab |
set myList = ##class(%ListOfObjects).%New() |
文字列、整数、または他のデータ型の配列 |
%ArrayOfDataTypesOpens in a new tab |
set myArray = ##class(%ArrayOfDataTypes).%New() |
オブジェクトの配列 |
%ArrayOfObjectsOpens in a new tab |
set myArray = ##class(%ArrayOfObjects).%New() |
リスト・コレクションの操作
以降のセクションの例は、リスト・プロパティを操作する方法を示していますが、同様の構文を使用してスタンドアロン・コレクションのリストを操作することができます。
リスト要素の挿入
要素をリストの末尾に挿入するには、Insert() メソッドを使用します。例えば、obj がオブジェクトへの参照であり、Colors が関連オブジェクトのリスト・プロパティであるとします。このプロパティの定義は以下のとおりです。
Property Colors as list of %String;
以下のコードは、3 つの要素をリストに挿入します。リストがそれまで空だった場合、これらの要素は位置 1、2、および 3 にそれぞれ配置されます。
do obj.Colors.Insert("Red") // key = 1
do obj.Colors.Insert("Green") // key = 2
do obj.Colors.Insert("Blue") // key = 3
要素をリスト内の特定の位置に挿入するには、InsertAt() メソッドを使用します。例えば、以下のコードは、obj の Colors プロパティの 2 つ目の位置に文字列 Yellow を挿入します。
do obj.Colors.InsertAt("Yellow",2)
これにより、このリストの要素の順序は "Red"、"Yellow"、"Green"、"Blue" になります。新しい要素は位置 2 に配置され、それまで位置 2 および 3 にあった要素 ("Green" および "Blue") が位置 3 および 4 に移動し、新しい要素の場所が作られます。
リスト要素の挿入は、オブジェクトに対しても同じように機能します。例えば、pat がオブジェクト参照であり、Diagnoses が関連オブジェクトのリスト・プロパティであるとします。このプロパティは、以下のように定義されています (PatientDiagnosis はクラスの名前です)。
Property Diagnoses as list of PatientDiagnosis;
以下のコードは、オブジェクト参照 patdiag に格納される、PatientDiagnosis の新しいクラス・インスタンスを作成し、このオブジェクトを Diagnoses リストの末尾に挿入します。
Set patdiag = ##class(PatientDiagnosis).%New()
Set patdiag.DiagnosisCode=code
Set patdiag.DiagnosedBy=diagdoc
Set status=pat.Diagnoses.Insert(patdiag)
リスト要素へのアクセス
リスト要素にアクセスするには、以下のコレクション・メソッドを使用します。
-
GetAt(key) – key で指定された位置にある要素の値を返します。
-
GetPrevious(key) – key の直前の位置にある要素の値を返します。
-
GetNext(key) – key の直後の位置にある要素の値を返します。
-
Find(value, key) – key の後から開始して、value に等しい次のリスト要素のキーを返します。
例えば、以下のコードは、リストを反復処理し、そのリストの要素を順番に表示します。コレクションの Count プロパティによって、反復処理する要素の数が決まります。
set p = ##class(Sample.Person).%OpenId(1)
for i = 1:1:p.FavoriteColors.Count() {write !, p.FavoriteColors.GetAt(i)}
リスト要素の変更
指定したキーにある値を変更するには、以下の構文で示すように、SetAt() メソッドを使用できます。
do oref.PropertyName.SetAt(value,key)
ここで、oref はオブジェクト参照であり、PropertyName はそのオブジェクトのリスト・プロパティの名前です。例えば、person.FavoriteColors は好きな色のリスト・プロパティであり、その要素として red、blue、および green があるとします。以下のコードは、リストの 2 つ目の色を yellow に変更します。
do person.FavoriteColors.SetAt("yellow",2)
リスト要素の削除
リスト要素を削除するには、RemoveAt() メソッドを使用します。例えば、person.FavoriteColors は好きな色のリスト・プロパティであり、その要素として red、blue、および green があるとします。以下のコードは、位置 2 にある要素 (blue) を削除します。
do person.FavoriteColors.RemoveAt(2)
これにより、このリストの要素の順序は red、green になります。それまで位置 3 にあった要素 (green) が位置 2 に移動し、削除された要素によって生じた空きが埋められます。
配列コレクションの操作
要素を配列に追加するには、SetAt() メソッドを使用します。例えば、myArray.SetAt(value,key) は、key の位置にある配列要素を、指定された value に設定します。以下のコードは、新しい色を RGB 値の配列に挿入します。
do palette.Colors.SetAt("255,0,0","red")
palette はこの配列を格納するオブジェクトへの参照、Colors は配列プロパティの名前、"red" は値 "255,0,0" にアクセスするキーです。
配列キーとして使用する値には、連続する 1 対の垂直バー (||) を含めないでください。この制限は、InterSystems SQL のメカニズムに起因しています。
SetAt() は、既存の要素の値を変更することもできます。例えば、以下のコードは、"red" キーに格納されている値を 16 進形式に変更します。
do palette.Colors.SetAt("#FF0000","red")
配列内のコンテンツを反復処理するには、キーを GetNext() メソッドに参照渡しします。これにより、キーと値の両方をループで反復処理できます。例えば、以下のコードは、文字列配列のキーと値を順番に書き込みます。要素は、キーのアルファベット順に並べられます。
set arr=##class(%ArrayOfDataTypes).%New()
do arr.SetAt("red","color")
do arr.SetAt("large","size")
do arr.SetAt("expensive","price")
set key=""
for {set value=arr.GetNext(.key) quit:key="" write !,key," = ",value}
color = red
price = expensive
size = large
コレクション・データのコピー
一方のコレクションにある項目を他方のコレクションにコピーするには、コピー先のコレクションの設定を、コピー元のコレクションの設定と同じものにします。 これにより、コピー元の内容が、コレクション自身の OREF ではなく、コピー先にコピーされます。 以下は、このコマンドの例です。
Set person2.Colors = person1.Colors
Set dealer7.Inventory = owner3.cars
ここで、person2、person1、dealer7、および owner3 は、すべてクラスのインスタンスで、Colors、Inventory、および cars は、すべてコレクションのプロパティです。このコードの 1 行目は、同じクラスにある 2 つのインスタンス間でデータをコピーし、2 行目は、互いに異なるクラスにあるインスタンスの間でデータをコピーします。
コピー先のコレクションがリストで、コピー元のコレクションが配列の場合、InterSystems IRIS では、配列のデータのみがコピーされます (キー値はコピーされません)。 コピー先のコレクションが配列で、コピー元のコレクションがリストの場合、InterSystems IRIS では、コピー先の配列にキー値が生成されます。このキー値は、コピー元リストの項目の位置に基づいた整数になります。
コレクションの間で OREF をコピーする方法はありません。データのコピーのみが可能です。