2011-06-11 132 views
75

我剛剛創建了一個單例方法,我想知道函數@synchronized()做什麼,因爲我經常使用它,但不知道含義。@synchronized()做了什麼?

+1

http://stackoverflow.com/q/6234344/277952可能的重複? – NSGod 2011-06-11 19:14:09

回答

103

它在代碼塊周圍聲明critical section。在多線程代碼中,@synchronized保證在任何給定時間只有一個線程可以在塊中執行該代碼。

如果您不知道它的功能,那麼您的應用程序可能不是多線程的,並且您可能不需要使用它(特別是如果單例本身不是線程安全的)。


編輯:添加一些是不是在原來的答案從2011年

@synchronized指令prevents multiple threads from entering any region of code that is protected by a @synchronized directive referring to the same object更多信息。傳遞給@synchronized指令的對象是用作「鎖」的對象。如果使用不同的對象作爲鎖,則兩個線程可以位於相同的受保護代碼區域中,並且還可以使用與鎖相同的對象來保護兩個完全不同的代碼區域。

此外,如果您碰巧將nil作爲鎖定對象,則根本不會執行鎖定。

+12

有幾點需要注意:1)如果你在'@ synchronized'中使用了一個零指針,它什麼都不做 - 你不受保護。 2)'@ synchronized'是* slow *。 – 2013-07-27 13:02:06

+0

這個答案是誤導性的,不應該被接受的答案。儘管它所說的有時是正確的(只要傳遞給* synhronized *的令牌在所有線程中都是同一個對象),它就會誤導性地不完整。 * synchronized *可以防止同時執行任何數量的關聯代碼段,而不僅僅是「塊中的代碼」。參數* synchronized *有效地確定哪些代碼段(或稱爲「塊」作爲回答調用它們)受到保護而不受併發訪問的影響。 – Arda 2017-03-20 17:20:29

+0

@Arda你是完全正確的。我已經添加了一些更多信息和一些關於'@ synchronized'的Apple文檔的鏈接。 – 2017-03-22 03:19:35

42

從Apple文檔herehere

的@Synchronized指令是在Objective-C代碼動態創建互斥鎖 一個 便捷的方式。 @synchronized指令執行任何其他互斥鎖都會執行的操作 - 它會阻止不同線程同時獲取相同的鎖。

該文檔提供了關於此主題的大量信息。花時間閱讀它是值得的,尤其是考慮到你一直在使用它而不知道它在做什麼。

25

@synchronized指令是一種方便快捷的方式在Objective-C代碼中創建互斥鎖。

@synchronized指令執行其他任何互斥鎖都會執行的操作 - 它可以防止不同線程同時獲取同一個鎖。

語法:

@synchronized(key) 
{ 
    // thread-safe code 
} 

實施例:

-(void)AppendExisting:(NSString*)val 
{ 
    @synchronized (oldValue) { 
     [oldValue stringByAppendingFormat:@"-%@",val]; 
    } 
} 

現在上面的代碼是完全線程safe..Now多個線程可以改變數值。

上面的僅僅是一個例子晦澀...

+3

不應該是@synchronized(oldValue)嗎? – Joel 2014-09-08 16:37:37

+0

甚至是'@synchronized(val,oldValue){...}'? – 2014-10-12 10:29:10

+0

我不知道我見過任何「完美線程安全」的方案。至少你需要知道你在做什麼,而不是盲目地從某個地方複製代碼。 – 2015-01-25 14:54:27

0

@synchronizedthread safe機制。在這個函數中寫入的代碼成爲critical section的一部分,一次只能執行一個線程。

@synchronize隱式應用鎖,而NSLock明確應用它。

它只保證線程安全,不能保證。我的意思是你爲你的汽車聘請了一位專家司機,但它並不能保證汽車不會遇到事故。然而,可能性仍然是絲毫的。

+1

這是完全錯誤的。 dispatch_once不會和@syncrhonized一樣,它可以是一個單獨的分配下的替代品。 – jugutier 2016-08-22 21:32:28