【问题标题】:get the string value only when it is set c#仅在设置 c# 时获取字符串值
【发布时间】:2013-08-22 20:49:45
【问题描述】:

在get set 属性中,只有在设置了值之后才返回值。我使用了响应式库并订阅了它在不同线程上运行的消息。当引发事件并设置值时,捕获该值并返回。

 internal PinMessage()
        {
            obj.PinsAvailable.ObserveOn(SynchronizationContext.Current).Subscribe(HandlePinsAvailable);
        }      

        private void HandlePinsAvailable(byte[] pinBytes)
        {
           pinmesssage = Encoding.ASCII.GetString(pinBytes);           
        }

        public void Readvalue(object stringobj)
        {
            pinmesssage = (string)stringobj;
        }

        internal string GetPinMessage(string AccoutNumber)
        {
            string pinstring = string.Empty;
            obj.SendPinRequest(AccoutNumber);
            t1.Join();
            pinstring = pinmesssage;
            return pinstring;
        }

        private string _pinMessafe;

        public string pinmesssage
        {
            get
            {
//Get value only when the property is set
                return _pinMessafe;
            }
            set { _pinMessafe = value; }
        }

【问题讨论】:

  • 问题是什么?
  • 如果是字符串,只检查_pinMessafe是否为空/空,如果为假则返回。
  • @tnw 假设你检查了它并且它不为空,并且在你返回它之前,另一个线程将它设置为空。
  • 我从设备获取 pinmesssage,当我获取数据时 GetPinMessage 返回 null。它不是在等待 pin 消息。
  • 您正在尝试使用 Rx 执行同步代码。那不是它的用途。您需要将此代码重构为异步的。一个可观察的和多个对 pin 消息的请求之间也存在严重的脱节。您需要将它们配对。

标签: c# multithreading get set system.reactive


【解决方案1】:

如果你想等待另一个线程设置一个值,你可以使用TaskCompletionSource

你在某处创建一个 TaskCompletionSource

TaskCompletionSource<string> tcs = new TaskCompletionSource<string>();

在产生你所做的价值的线程上

tcs.SetResult("some string message");

在线程上等待你做的结果

string message = tcs.Task.Result; // Will block the current thread

或者在异步方法中更好地使用async await pattern

string message = await tcs.Task

但是如果你真的在使用Reactive Extensions 那么你应该 可能将它用于整个管道而不是上述模式。 你可能应该写

string message = await MessageSource().Take(1);

MessageSource 的签名位置

IObservable<string> MessageSource();

【讨论】:

  • 这真的很有用我不能投票,我是新手。我需要它的原因是我有异步线程,我必须将它们同步到一个方法中。这样我就可以在方法中发送消息后返回一个值。目前我正在使用 onObserve ,当数据可用时检索它。我正在构建一个库,我在其中发送消息并接收数据 CLASSIC STYLE
【解决方案2】:

你在这里混合了很多东西。当您使用 Rx 时,您不会尝试通过执行线程连接来编组线程。您无需进出 Rx 代码。

您的代码应该如下所示:

internal IObservable<string> GetPinMessage(string AccoutNumber)
{
    return Observable
        .Start(() => obj.SendPinRequest(AccoutNumber))
        .Select(pinBytes => Encoding.ASCII.GetString(pinBytes))
        .ObserveOn(SynchronizationContext.Current);
}

我假设SendPinRequest 是一个同步请求。 Rx 会为你把它变成一个单值的异步 observable。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-12-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-02-16
    相关资源
    最近更新 更多