ここは旧式の4DドキュメントWebサイトです。最新のアップデートされたドキュメントを読むには新サイトをご利用下さい→ developer.4d.com

ホーム

 
4D v19.8
共有オブジェクトと共有コレクション

共有オブジェクトと共有コレクション  


 

定義  

共有オブジェクトおよび共有コレクションはプロセス間でコンテンツを共有することができる、特殊なオブジェクトとコレクションです。に比べると、共有オブジェクトと共有コレクションはプリエンプティブ4Dプロセスと互換性があるという点で利点があります。つまり、New processCALL WORKERといったコマンドに、参照によって引数として渡すことができるということです。

共有オブジェクトと共有コレクションは標準のC_OBJECTC_COLLECTIONコマンドで宣言された変数に保存することができますが、特定のコマンドを使用してインスタンス化されている必要があります:

  • 共有オブジェクトを作成するには、New shared object コマンド、またはOB Copy コマンドとck shared オプションを使用してください。
  • 共有コレクションを作成するには、New shared collection コマンド、またはcollection.copy( ) メソッドとck shared オプションを使用してください。

注: 共有オブジェクトと共有コレクションは標準(非共有)オブジェクトおよびコレクションのプロパティとして設定することができます。

共有オブジェクト/コレクションを編集するためには、Use...End use 構造を呼ぶ必要があります。共有オブジェクト/コレクションの値を読みだすためには、Use...End use は必要ありません。

Storage コマンドから返される、固有の、グローバルなカタログは、データベース内あるいはコンポーネントからいつでも利用することができ、全ての共有オブジェクトおよびコレクションを保存するのに使用することができます。

New shared object あるいは New shared collection コマンドでインスタンス化されると、共有オブジェクト/コレクションの属性と要素はどのプロセスからでも編集/読み出しができるようになります。

編集  

共有オブジェクトと共有コレクションは、編集することが可能です:

  • オブジェクトプロパティを追加あるいは削除する
  • 値を追加あるいは編集する (共有オブジェクトがサポートしている範囲内で)。これには、他の共有オブジェクトやコレクションへの追加・編集も含まれます(この場合共有グループを作成します。以下参照)

ただし、共有オブジェクトあるいは共有コレクションを編集するコードは、必ずUse...End use キーワードでくくられている必要があり、そうでない場合にはエラーが返されます。

 $s_obj:=New shared object("prop1";"alpha")
 Use($s_obj)
    $s_obj.prop1:="omega"
 End Use

共有オブジェクト/コレクションは一度に1プロセスずつしか編集することができません。Use は共有オブジェクト/コレクションを他のスレッドからアクセスできないようにロックする一方、End use は共有オブジェクト/コレクションのロックを解除します(ただしロッキングカウンターが0であれば。詳細は以下参照)。全てのオブジェクトとコレクションのロックを解除します。Use...End use が一つもない状態で共有オブジェクト/コレクションを編集しようとすると、エラーが生成されます。あるプロセスが、すでに他のプロセスによって使用されている共有オブジェクト/コレクションに対してUse...End use を呼び出した場合、その呼び出しはEnd use でロックが解除されるまで待機状態になります(エラーは生成されません)。結果として、Use...End use 構造内の編集は迅速に実行され、要素のロックは可及的速やかに解除される必要があります。そのため、共有オブジェクト/コレクションをインターフェース(ダイアログボックスなど)から直接編集することは避けることが強く推奨されます。

共有オブジェクト/コレクションを他の共有オブジェクト/コレクションのプロパティあるいは要素に割り当てることは可能で、このとき共有グループが作成されます。共有グループは、共有オブジェクト/コレクションが、他の共有オブジェクト/コレクションのプロパティ値あるいは要素として設定されたときに自動的に作成されます。共有グループを使用すると共有オブジェクトを入れ子にすることができますが、以下の追加のルールに気をつける必要があります:

  • グループの共有オブジェクト/コレクションに対してUse を呼び出すと、同じグループに所属する全ての共有オブジェクト/コレクションのプロパティ/要素がロックされ、ロッキングカウンターが1増加されます。End use を呼び出すと、グループのロッキングがカウンターが1減少し、カウンターが0になると、リンクされている全ての共有オブジェクト/コレクションのロックが解除されます。
  • 共有オブジェクト/コレクションは一つの共有グループにしか所属することができません。すでにグループに所属している共有オブジェクト/コレクションを他のグループへと割り当てようとした場合、エラーが返されます。
  • グループ化された共有オブジェクト/コレクションはグループを解除することはできません。一度共有グループに含まれた共有オブジェクト/コレクションは、セッション中はずっとグループに所属することになります。親オブジェクト/コレクションからあるオブジェクト/コレクションへの全ての参照が解除されたとしても、リンクは解除されるわけではありません。

共有グループのルールについて説明している例題2を参照してください。

注: 共有グループは、ロック識別子と呼ばれる内部プロパティを通して管理されています。これの詳細については、以下にある上級者向けのロック識別子 の章を参照してください。

共有オブジェクト/コレクションのプロパティあるいは要素は、たとえ共有オブジェクト/コレクションが他のプロセスから使用されている時であっても、Use...End use 構造を呼び出さずとも読み出すことが可能です。

しかしながら、複数の値が互いにリンクされていてそれら全てを一度に読み出す必要がある場合には、一貫性の観点から、共有オブジェクト/コレクションをUse...End use 内で読み出す必要があります。

複製  

デフォルトでは、OB Copy /collection.copy( ) を共有オブジェクト/共有コレクション(あるいは共有オブジェクト/共有コレクションを格納しているもの)で呼びと、返されるオブジェクトは、標準(非共有)のオブジェクト/コレクションとなり、格納されているオブジェクトがあればそれが含まれています。

しかしながら、これらのコマンドに対してoption 引数にck shared 定数を使用することで、ソースのオブジェクト/コレクションの共有コピーを生成することができます。

ストレージは固有の共有オブジェクトで、それぞれのアプリケーションとマシン上で利用可能です。この共有オブジェクトはStorage コマンドから返されます。このオブジェクトは、他のプリエンティブあるいは標準プロセスからでも利用出来るようにセッション中に定義された全ての共有オブジェクト/コレクションを参照するためのものです。

標準の共有オブジェクトとは異なり、共有オブジェクト/コレクションがプロパティとして追加されたときでも共有グループを作成しないという点に注意してください。この振る舞いにより、ストレージオブジェクトを使用するたびに接続された共有オブジェクト/コレクションを全てロックせずに済みます。

詳細な情報については、Storage コマンドの詳細を参照してください。

異なる製品の目録タスクを実行する複数のプロセスを起動し、同じ共有オブジェクトを更新するようにしたい場合を考えます。ここではメインプロセスで空の共有オブジェクトをインスタンス化し、他のプロセスに共有オブジェクトをと数える製品を引数として渡して起動します:

 ARRAY TEXT($_items;0)
 ... //数える製品を配列に入れる
 $nbItems:=Size of array($_items)
 C_OBJECT($inventory)
 $inventory:=New shared object
 Use($inventory)
    $inventory.nbItems:=$nbItems
 End use
 
  //プロセスを作成していく
 For($i;1;$nbItems)
    $ps:=New process("HowMany";0;"HowMany_"+$_items{$i};$_items{$i};$inventory)
  //$inventory オブジェクトを参照で渡す
 End for

"HowMany" メソッドでは、目録の作成が終わるとすぐに$inventory 共有オブジェクトは更新されます:

 C_TEXT($1)
 C_TEXT($what)
 C_OBJECT($2)
 C_OBJECT($inventory)
 $what:=$1 //読みやすさのため
 $inventory:=$2
 
 $count:=CountMethod($what//製品を数えるメソッド
 Use($inventory//共有オブジェクトを使用
    $inventory[$what]:=$count  //この製品に対する結果を保存
 End use

以下の例題は、共有グループを扱う際の特定のルールについて説明しています:

 $ob1:=New shared object
 $ob2:=New shared object
 Use($ob1)
    $ob1.a:=$ob2  //グループ1が作成される
 End use
 
 $ob3:=New shared object
 $ob4:=New shared object
 Use($ob3)
    $ob3.a:=$ob4  //グループ2が作成される
 End use
 
 Use($ob1//グループ1のオブジェクトを使用
    $ob1.b:=$ob4  //これはエラーとなる
  //$ob4 は他のグループに既に所属しているため
  //代入は不可能
 End use
 
 Use($ob3)
    $ob3.a:=Null //グループ2から$ob4 への参照をすべて解除
 End use
 
 Use($ob1//グループ1のオブジェクトを使用
    $ob1.b:=$ob4  //これもエラーとなる
  //$ob4 は依然としてグループ2に所属している
  //そのため代入は不可能
 End use

注: この章では4D の内部的な機構についての詳細な情報を提供しており、これは特定の場合においてのみ有効です。

全ての新規の共有のオブジェクト/コレクションは固有のロック識別子(倍長整数値)とともに作成されます。初期のステータスは常に負の値になり、これは共有オブジェクト/コレクションが"single"というステータスであることを意味します。"single" ステータスの共有オブジェクト/コレクションが他の共有オブジェクト/コレクションのプロパティあるいは要素として設定された場合、どちらもステータスは"multiple"となり、共有グループが作成されます。どちらも同じロック識別子を共有し(追加された属性/要素は親オブジェクト/コレクションのロック識別子を継承します)、ロック識別子の値は正の値になります。

共有オブジェクト/コレクションがその親オブジェクト/コレクションから削除された場合:
  • それでもそれらのステータスは"multiple"とみなされます。
  • 同じロック識別子を共有します。

共有オブジェクト/コレクションを他の共有オブジェクト/コレクションの属性あるいは要素として設定する場合には、以下のルールが適用されます:

  • "single" のオブジェクト/コレクションは、他の"single"あるいは"multiple" のオブジェクト/コレクションに割り当てることができます。
  • "multiple" のオブジェクト/コレクションは、同じロック識別子を持つ"multiple" のオブジェクト/コレクションに割り当てることができます。
  • "multiple" のオブジェクト/コレクションを他の"single"あるいは"multiple" ステータスの、同じロック識別子を持たないオブジェクト/コレクションに割り当てると、エラーが生成されます。

上記のルールは、以下の図において解説されています:

  1. 共有オブジェクトと共有コレクション(A, B, C, D)はそれぞれ、固有の負の値の"ロック識別子"(緑)を持って作成されています。
  2. "single"のオブジェクト(A)が他の"single"のオブジェクト(B)を内部に参照している場合、それらはどちらも"multiple"となり、同じ正の値のロック識別子(赤)を共有します。このとき追加の"single"のオブジェクトを(A)内部に、(B)とならんで、あるいは(B)内部に追加することもできます。全てのオブジェクトは"multiple"とみなされ、同じロック識別子を共有します。
  3. "multiple"であるオブジェクト(B)が、他の"multiple"のオブジェクト(A)から削除された(参照されなくなった)場合、どちらのオブジェクトも引き続き"multiple"を維持し、同じロック識別子を共有し続けます。
  4. "multiple"のオブジェクト(A, B)を"single"のオブジェクト(D)の属性として使用することはできませんが、"single"のオブジェクト(C)は使用することができます。
  5. "multiple"のオブジェクト(A, B)は、同じロック識別子を共有するオブジェクト(D)に対しては、(D)の属性として使用することができます。"single"のオブジェクト(C)も(D)の属性として使用することができます。

共有オブジェクト/コレクションのロック識別子は、デバッガ内にて__LockerID というプライベートプロパティとして表示されます。デバッガのコンテキストメニューで"型を表示"を選択することで"共有オブジェクト"型を表示させることができます:

共有オブジェクト/コレクションは、それらがどこでも"使用中"でない限りは、デバッガからも直接入力可能であることに注意してください。使用中の場合には共有オブジェクト/コレクションの編集はできません。



参照 

collection.copy( )
New shared collection
New shared object
OB Copy
Storage

 
プロパティ 

プロダクト: 4D
テーマ: オブジェクト(ランゲージ)

 
ページの目次 
 
履歴 

初出: 4D v16 R6

 
ARTICLE USAGE

ランゲージリファレンス ( 4D v19)
ランゲージリファレンス ( 4D v19.1)
ランゲージリファレンス ( 4D v19.4)
ランゲージリファレンス ( 4D v19.5)
ランゲージリファレンス ( 4D v19.6)
ランゲージリファレンス ( 4D v19.7)
ランゲージリファレンス ( 4D v19.8)