Subject 類型實現(xiàn)IObservable 和IObserver ,在它既是觀察者又是可觀察者的意義上。您可以使用主題訂閱所有觀察者,然后將主題訂閱到后端數(shù)據(jù)源。以這種方式,主體可以充當一組訂戶和源的代理。你可以使用主題實現(xiàn)一個自定義observable與緩存,緩沖和時間移位。此外,您可以使用主題向多個訂閱者廣播數(shù)據(jù)。 默認情況下,主題不通過線程執(zhí)行任何同步。他們不采取調(diào)度程序,而是假定所有序列化和語法正確性由主體的調(diào)用者處理。主題簡單地廣播到線程安全的訂戶列表中的所有訂閱的觀察者。這樣做具有減少開銷和提高性能的優(yōu)點。但是,如果要使用調(diào)度程序?qū)鞒稣{(diào)用同步到觀察者,則可以使用同步方法執(zhí)行此操作。
在以下示例中,我們創(chuàng)建一個主題,訂閱該主題,然后使用相同的主題向觀察者發(fā)布值。 通過這樣做,我們將發(fā)布和訂閱組合到同一個源中。 除了獲取IObserver ,Subscribe方法還有一個重載,它對onNext采用Action ,這意味著每次發(fā)布項目時都會執(zhí)行該操作。 在我們的示例中,每當OnNext被調(diào)用時,該項目將被寫入控制臺。
Subject<int> subject = new Subject<int>();var subscription = subject.Subscribe( x => Console.WriteLine("Value published: {0}", x), () => Console.WriteLine("Sequence Completed."));subject.OnNext(1);subject.OnNext(2);Console.WriteLine("PRess any key to continue");Console.ReadKey();subject.OnCompleted();subscription.Dispose();以下示例說明了Subject的代理和廣播性質(zhì)。 我們首先創(chuàng)建一個源序列,每1秒產(chǎn)生一個整數(shù)。 然后我們創(chuàng)建一個Subject,并將它作為觀察者傳遞給源,以便它將接收由該源序列推出的所有值。 之后,我們創(chuàng)建另外兩個訂閱,這次以主題為源。 然后,subSubject1和subSubject2訂閱將接收Subject發(fā)送的任何值(從源)。
var source = Observable.Interval(TimeSpan.FromSeconds(1));Subject<long> subject = new Subject<long>();var subSource = source.Subscribe(subject);var subSubject1 = subject.Subscribe( x => Console.WriteLine("Value published to observer #1: {0}", x), () => Console.WriteLine("Sequence Completed."));var subSubject2 = subject.Subscribe( x => Console.WriteLine("Value published to observer #2: {0}", x), () => Console.WriteLine("Sequence Completed."));Console.WriteLine("Press any key to continue");Console.ReadKey();subject.OnCompleted();subSubject1.Dispose();subSubject2.Dispose();Rx庫中的Subject 類型是ISubject 接口的基本實現(xiàn)(您也可以實現(xiàn)ISubject 接口來創(chuàng)建自己的主題類型)。還存在提供不同功能的ISubject 的其他實現(xiàn)。所有這些類型存儲通過OnNext推送到它們的一些(或所有)值,并將其廣播回其觀察者。這樣,他們將熱觀察變?yōu)槔溆^察。這意味著,如果您多次訂閱這些內(nèi)容(即訂閱 - >取消訂閱 - >再次訂閱),您將再次看到至少一個相同的值。有關熱觀察和冷觀察的更多信息,請參閱創(chuàng)建和訂閱簡單可觀察序列主題中的最后一節(jié)。 ReplaySubject存儲它已發(fā)布的所有值。因此,當您訂閱它時,您會自動收到已發(fā)布的值的完整歷史記錄,即使您的訂閱可能在某些值被推出后才進入。 BehaviourSubject類似于ReplaySubject,除了它只存儲它發(fā)布的最后一個值。 BehaviourSubject在初始化時還需要類型T的默認值。當主體尚未接收到其他值時,此值將發(fā)送給觀察者。這意味著所有訂閱者都將在訂閱時立即收到一個值,除非主題已經(jīng)完成。 AsyncSubject類似于Replay和Behavior主題,但它將僅存儲最后一個值,并且只在序列完成時發(fā)布。對于源可觀察程序熱的情況,可以使用AsyncSubject類型,并且可以在任何觀察者訂閱之前完成。在這種情況下,AsyncSubject仍然可以提供最后一個值,并將其發(fā)布到任何未來的訂閱者。
返回列表
新聞熱點
疑難解答