0

重複の可能性:
In属性とOut属性は.NETでどのように機能しますか?

.Net Remoting(ええ、私は知っています...それは古いです)を使用して、Windowsサービスでホストされているサービスクラスを実装しています。

以下のコードのように、サービスのメソッドを呼び出してDoOperation(Person[] people)、クラスの一部のプロパティを変更します。Person

Person p = new Person();
p.SomeProperty = "This value should be changed by the service";

RemoveSvc svc = (RemoveSvc)Activator.GetObject(
    typeof(RemoveSvc),
    "tcp://localhost:6100/RemoteService.rem");

svc.DoOperation(new Person[]{ p });

// This writes the old value not the one changed by the service.
Console.WriteLine(p.SomeProperty); 

メソッドコードは次のDoOperationようになります。

public void DoOperation(Person[] people) {
    foreach(var o in people)
        p.SomeProperty = "New Value";
}

ここでの問題は、メソッドがを返すときに、の値がPerson.SomePropertyクライアントコードで更新されないことです。

Personクラスがシリアライズ可能であることを再確認しました。

svc変数のタイプはTranparentProxy;

クラスはRemoteSvc継承しMarshalByRefObjectます;

.net Framework 4を使用しています(いいえ、WCFに移行できません)

私は何が間違っているのですか?これは.netRemotingの予想される動作ですか?もしそうなら、それを変更する方法はありますか?

Tks

4

2 に答える 2

2

それはサービスがどのように機能するかではありません。サービスはメモリ内操作ではありません。ローカルマシンで作成したクラスで表示したことを実行するPersonと、呼び出し元とメソッドの間でメモリ参照を渡すため、オブジェクトへの変更が自然に表示されます。当然、それはまったく同じ人物オブジェクトです。

ただし、サービスやリモーティングを使用すると、同じ人物ではなくなります。実際、あなたはあなたの質問でこれを述べています。あなたはその人をシリアル化し、それをネットワークを介して出荷します。同じ共有メモリレジスタ内の同じ人物ではありません。そのため、サーバー上の変更Personはクライアントには表示されません。

必要なものを取得するために、ここに関数のシグネチャがあります。

public Person[] DoOperation(Person[] people);

参照を保持するように署名を変更できます。その後、オブジェクトはクライアントのサーバー間で同期されたままになります。詳細については、この記事を参照してください。

public void DoOperation(ref Person[] people);
于 2012-10-30T18:40:36.053 に答える
0

ジャレットは正しいですが、それは解決策の一部にすぎないかもしれません。問題は、配列への参照を渡しても、Person配列内にsをコピーしたままであるということです。したがって、それらの1つをリモートで変更しても、ローカルコピーには影響しません。ローカル参照を使用するのではなく、配列を介してそれらを参照する必要がある場合があります。

私は次のようなことを試みます:

var temp = new Person[]{ p }
svc.DoOperation(temp);

// This writes the old value not the one changed by the service.
Console.WriteLine(temp[0].SomeProperty); 

Personこれは、ローカル参照を使用するのではなく、リモートロケーションからフェッチするためにリモート呼び出しによって作成されたプロキシを使用する場合があります。

于 2012-10-30T20:13:58.297 に答える