シーケンスデータオブジェクトの使用

シーケンスデータオブジェクトは、データオブジェクト内のさまざまな プロパティの並び順を追跡する SDO です。ここには、非構造化 テキスト要素 (SDO のいずれのプロパティにも属さないテキスト要素) を含めることも可能です。シーケンスデータオブジェクトは、 非構造化テキストを許可 (つまり、mixed=true である) したり、要素が交互に現れる (

<A/><B/><A/>
) ような XML 文書を扱う場合に有用です。 これは、例えば order に choice を指定した複合型の要素に対して スキーマで maxOccurs>1 を定義している場合などに発生します。

以下の例では、XML データアクセスサービスを使用して、 下のスキーマおよびインスタンスをもとに作成した SDO の使用を想定しています。

このスキーマでは、手紙の書式を定義しています。letter (手紙) には オプションで 3 つのプロパティ date (日付)、firstName (名前)、 および lastName (苗字) を含めることが可能です。このスキーマでは mixed="true" としていますが、これは 3 つのプロパティの間に非構造化テキストをちりばめることが できるということを意味します。

<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema"
  xmlns:letter="http://letterSchema"
  targetNamespace="http://letterSchema">
  <xsd:element name="letters" type="letter:FormLetter"/>
  <xsd:complexType name="FormLetter" mixed="true">
    <xsd:sequence>
      <xsd:element name="date" minOccurs="0" type="xsd:string"/>
      <xsd:element name="firstName" minOccurs="0" type="xsd:string"/>
      <xsd:element name="lastName" minOccurs="0" type="xsd:string"/>
    </xsd:sequence>
  </xsd:complexType>
</xsd:schema>

以下が、手紙のインスタンスです。これには 3 つのプロパティ date、firstName および lastName が含まれており、非構造化 テキスト要素として住所と本文が含まれています。

<letter:letters xmlns:letter="http://letterSchema">
  <date>March 1, 2005</date>
  Mutual of Omaha
  Wild Kingdom, USA
  Dear
  <firstName>Casy</firstName>
  <lastName>Crocodile</lastName>
  Please buy more shark repellent.
  Your premium is past due.
</letter:letters>

このインスタンスが読み込まれると、letter データオブジェクトの シーケンス番号およびプロパティ番号は以下の表のようになります。

シーケンスのインデックス プロパティのインデックス:名前
0 0:date March 1, 2005
1 - Mutual of Omaha
2 - Wild Kingdom, USA
3 - Dear
4 1:firstName Casy
5 2:lastName Crocodile
6 - Please buy more shark repellent.
7 - Your premium is past due.

シーケンス番号の整合性を保つため、シーケンスデータオブジェクトの 操作には SDO_Sequence インターフェイスを使用しなければなりません。 これにより、データオブジェクトに対しての操作を プロパティのインデックスではなくシーケンスのインデックスを使用して 行えるようになります (上の表を参照ください)。 以下の例では、letter のインスタンスが データオブジェクト $letter として 読み込まれているものと仮定します。

例1 SDO_Sequence インターフェイスの取得

データオブジェクトのシーケンスを取得するには getSequence() メソッドを使用します。 以下の例では、letter データオブジェクトのシーケンスを取得します。

<?php
  $letter_seq 
$letter->getSequence();
?>

これ以降の例では、letter データオブジェクトのシーケンスが 変数 $letter_seq に代入されているものとします。

例2 シーケンスの値の取得/設定

シーケンスのインデックスを使用することで、(非構造化 テキストも含め) それぞれの値を取得したり設定したりすることが可能です。 以下の例では、ファーストネームを 'Snappy' に変更して シーケンスの最後の値 (非構造化テキスト 'Your premium is past due.') を取得します。

<?php
  $letter_seq
[4] = 'Snappy';
  
$text $letter_seq[count($letter_seq) - 1];
?>

例3 シーケンスの繰り返し処理

foreach を使用して、個々のシーケンス値について処理を繰り返すことが できます。以下の例では、シーケンス順に個々の値を処理します。

<?php
foreach ($letter->getSequence() as $value) {
    
// ...
}
?>

例4 シーケンスとデータオブジェクトの比較

データオブジェクトのインターフェイスから設定した値は、シーケンスの 一部とはならないことがあります。データオブジェクト経由で値を 設定した場合、そのプロパティが既にシーケンスに組み込まれていた 場合にのみシーケンスからアクセス可能となります。 以下の例では、データオブジェクト経由で lastName を設定して それをシーケンスから取得しています。これがうまくいくのは、 lastName が既にシーケンス内に存在するからです。もしこれが 事前に設定されていなかった場合、lastName には 'Smith' が 設定されますが、それはシーケンスの一部とはなりません。

<?php
  $letter
[2] = 'Smith';
  
$last_name $letter_seq[5];
?>

例5 シーケンスへの追加

シーケンスに新しい値を追加するには SDO_Sequence::insert() メソッドを使用します。以下の例では、プロパティ 'firstName' および 'lastName' が最初に削除されているものと仮定します。

<?php
  
// シーケンスに firstName を追加します
  // 値: 'Smith'
  // シーケンスのインデックス: NULL (追加)
  // プロパティ ID: 1 (firtName プロパティのインデックス)
  
$letter_seq->insert('Smith'NULL1);

  
// シーケンスに lastName を追加します
  // 値: 'Jones'
  // シーケンスのインデックス: NULL (追加)
  // プロパティ ID: 'lastName' (lastName プロパティの名前)
  
$letter_seq->insert('Jones'NULL'lastName');

  
// 非構造化テキストを追加します
  // 値: 'Cancel Subscription.'
  // シーケンスのインデックス: 省略 (追加)
  // プロパティ ID: 省略 (非構造化テキスト)
  
$letter_seq->insert('Cancel Subscription.');

  
// 非構造化テキストを間に挿入します。それ以降のシーケンス値は
  // ひとつずれます。
  // 値: 'Care of:'
  // シーケンスのインデックス: 1 (2 番目の要素として挿入する)
  // プロパティ ID: 省略 (非構造化テキスト)
  
$letter_seq->insert('Care of:'1);
?>

例6 シーケンスからの削除

シーケンスに項目が登録されているかどうかを確かめたり シーケンスから項目を削除したりする際には、それぞれ isset() および unset() 関数が使用可能です (注意: unset() は、現時点では値を データオブジェクト内に残します。しかし、この挙動はおそらく今後 変更され、データオブジェクトからもデータを削除することに なるでしょう)。シーケンスの挙動は、リスト構造に似ています。 そのため、シーケンスの途中の項目を削除すると、それ以降の インデックスがひとつずつ小さいほうにずれます。以下の例では、 インデックスの最初の要素が存在するかどうか調べ、存在する場合に それを削除しています。

<?php
  
if (isset($letter_seq[0])) {
    unset(
$letter_seq[0]);
  }
?>