C# 组合观测值

C# 组合观测值,c#,system.reactive,C#,System.reactive,我有两个可观察对象:LoadLocal和LoadServer。LoadLocal从本地源加载并返回元素,LoadServer从服务器获取该元素。我想把它们组合成另一个可观察的对象:负载。我希望Load从LoadLocal获取元素,如果为null,我希望从LoadServer返回元素。有什么办法吗 谢谢 真实场景的详细信息: // loadLocal(id) gives me an observable that returns an asset from a local source Func

我有两个可观察对象:LoadLocal和LoadServer。LoadLocal从本地源加载并返回元素,LoadServer从服务器获取该元素。我想把它们组合成另一个可观察的对象:负载。我希望Load从LoadLocal获取元素,如果为null,我希望从LoadServer返回元素。有什么办法吗

谢谢


真实场景的详细信息:

// loadLocal(id) gives me an observable that returns an asset from a local source
Func<Guid, IObservable<IAsset>> loadLocal = Observable.ToAsync<Guid, IAsset>(id => GetLocalAsset(id));

var svcClient = new ServiceClient<IDataService>();
var svc = Observable.FromAsyncPattern<Request, Response>(svcClient.BeginInvoke, svcClient.EndInvoke);

// calling loadServer(id) gives me an observable that returns an asset from a server
var loadServer = id => from response in svc(new Request(id)) select response.Asset;

// so at this point i can call loadServer(id).Subscribe() to get an asset with specified id from the server, or I can call loadLocal(id).Subscribe() to get it from local source.
// however I want another observable that combines the two so I can do: load(id).Subscribe() that gets the asset from loadLocal(id) and if it is null it gets it from loadServer(id)
var load = ???

大概是这样吧

var load = LoadLocal.Zip(LoadServer, (local, server) => local ?? server);
这个怎么样:

loadLocal(id)
    .Where(x => x != null)
    .Concat(Observable.Defer(() => loadServer(id)))
    .Take(1);

谢谢,试过了,效果不错。但是,即使LoadLocal返回元素,它仍然会尝试从服务器(LoadServer)获取元素(关键是如果元素可以在本地获取,则避免不必要的往返服务器)。@Pking,实际上我不确定我是否理解您试图做的事情。。。Martin的评论是正确的:你不能从一个可观察的对象中获取值。用真实场景的细节更新了这个问题。很有可能我处理这个问题的方式不对。“获取”是指可观察对象本身所做的工作。当您使用
IObservable
时,您不会“获取”值。而是在创建新值时(通过
Subscribe
)调用您。我真的不明白你的问题,所以也许你可以提供更多关于你的可观察对象的细节以及它们是如何一起发挥作用的?用真实场景的细节更新了这个问题。我找到了一个解决方案:var load=id=>from localAsset in loadLocal(id)from asset in(localAsset!=null?Observable.Return(localAsset):loadServer(id))选择资产@Pking,那么你应该把它作为一个答案发布并接受它。谢谢,除了我在原始帖子的评论中提到的解决方案之外,这也是有效的。
loadLocal(id)
    .Where(x => x != null)
    .Concat(Observable.Defer(() => loadServer(id)))
    .Take(1);