多線程

多線程

標籤(空格分隔): 網絡多線程


基礎概念

進程

  • 進程是指在系統中正在運行的一個應用程序
  • 每個進程之間是獨立的,每個進程均運行在其專用且受保護的內存空間內
  • 例如當我們打開微信的時候系統就會開啓一個進程

線程

  • 1個進程要想執行任務,必須得有線程(每1個進程至少要有1條線程)
  • 一個進程(程序)的所有任務都在線程中執行(當我們使用酷我播放音樂,打開迅雷下載資源,這些都是在線程中執行的)

線程的串行

  • 個線程中任務的執行是串行的
    • 如果要在1個線程中執行多個任務,那麼只能一個一個地按順序執行這些任務
    • 也就是說,在同一時間內,1個線程只能執行1個任務

多線程

  • 1個進程中可以開啓多條線程,多條線程可以並行(同時)執行不同的任務
  • 多線程技術可以提高程序的執行效率(比如迅雷同時下載幾個文件)

  • 實現原理:

    • 同一時間,CPU只能處理1條線程,只有1條線程在工作(執行),多線程併發(同時)執行,其實是CPU快速地在多條線程之間調度(切換),如果CPU調度線程的時間足夠快,就造成了多線程併發執行的假象
    • 所以線程不能太多,不然cpu的頻繁切換大量消耗了cpu的資源,線程的執行效率就會變低
  • 優點:能適當提高程序的執行效率,能適當提高資源利用率(CPU、內存利用率)
  • 缺點:
    • 創建線程是有開銷的,iOS下主要成本包括:內核數據結構(大約1KB)、棧空間(子線程512KB、主線程1MB,也可以使用-setStackSize:設置,但必須是4K的倍數,而且最小是16K),創建線程大約需要90毫秒的創建時間
    • 如果開啓大量的線程,會降低程序的性能
    • 線程越多,CPU在調度線程上的開銷就越大
    • 程序設計更加複雜:比如線程之間的通信、多線程的數據共享

多線程在iOS開發中的應用

主線程

  • 一個iOS程序運行後,默認會開啓1條線程,稱爲“主線程”或“UI線程”
  • 主線程的作用
    • 顯示\刷新UI界面
    • 處理UI事件(比如點擊事件、滾動事件、拖拽事件等
  • 主線程的使用注意
    • 別將比較耗時的操作放到主線程中
    • 耗時操作會卡住主線程,嚴重影響UI的流暢度,給用戶一種“卡”的壞體驗

NSThread

  • 一個NSThread對象就代表一條線程
  • 創建、啓動線程
NSThread *thread = [[NSThread alloc] initWithTarget:self selector:@selector(run) object:nil];
[thread start];
  • 獲取當前線程
    NSThread *current = [NSThread currentThread];
  • 線程的名字
    - (void)setName:(NSString *)n;
  • 其他創建線程方式

    • 創建線程後自動啓動線程
      [NSThread detachNewThreadSelector:@selector(run) toTarget:self withObject:nil];

    • 隱式創建並啓動線程
      [self performSelectorInBackground:@selector(run) withObject:nil];

線程狀態

  • 線程狀態:

- (void)start;
// 進入就緒狀態 -> 運行狀態。當線程任務執行完畢,自動進入死亡狀態

+ (void)sleepUntilDate:(NSDate *)date;
+ (void)sleepForTimeInterval:(NSTimeInterval)ti;
// 進入阻塞狀態

+ (void)exit;強制停止線程
// 進入死亡狀態

多線程安全隱患

  • 資源共享

    • 1塊資源可能會被多個線程共

      • 比如多個線程訪問同一個對象、同一個變享,也就是多個線程可能會訪問同一塊資源量、同一個文件
    • 當多個線程訪問同一塊資源時,很容易引發數據錯亂和數據安全問題

安全隱患解決 – 互斥鎖

  • 互斥鎖使用格式:
    @synchronized(鎖對象) { // 需要鎖定的代碼 }
    注意:鎖定1份代碼只用1把鎖,用多把鎖是無效的

  • 互斥鎖的優缺點

    • 優點:能有效防止因多線程搶奪資源造成的數據安全問題
    • 缺點:需要消耗大量的CPU資源
  • 互斥鎖的使用前提:多條線程搶奪同一塊資源

線程同步的意思是:多條線程在同一條線上執行(按順序地執行任務)
- 互斥鎖,就是使用了線程同步技術(線程同步的意思是:多條線程在同一條線上按順序地執行任務)

原子和非原子屬性

  • OC在定義屬性時有nonatomic和atomic兩種選擇
    atomic:原子屬性,爲setter方法加鎖(默認就是atomic)
    nonatomic:非原子屬性,不會爲setter方法加鎖
  • nonatomic和atomic對比

    • atomic:線程安全,需要消耗大量的資源
    • nonatomic:非線程安全,適合內存小的移動設備
  • iOS開發的建議:

    • 所有屬性都聲明爲nonatomic
    • 儘量避免多線程搶奪同一塊資源
    • 儘量將加鎖、資源搶奪的業務邏輯交給服務器端處理,減小移動客戶端的壓力
  • 注意點:
    • atomic系統自動給我們添加的鎖不是互斥鎖其實是自旋鎖
    • 互斥鎖和自旋鎖共同點
      • 都能夠保證多線程在同一時候, 只能有一個線程操作鎖定的代碼
    • 互斥鎖和自旋鎖不同點
      • 如果是互斥鎖, 假如現在被鎖住了,那麼後面來得線程就會進入”休眠”狀態, 直到解鎖之後, 又會喚醒線程繼續執行
      • 如果是自旋鎖, 假如現在被鎖住了, 那麼後面來得線程不會進入休眠狀態, 會一直傻傻的等待, 直到解鎖之後立刻執行
      • 自旋鎖更適合做一些較短的操作

線程間的通信

  • 在1個進程中,線程往往不是孤立存在的,多個線程之間需要經常進行通信

  • 線程間通信的體現

    • 1個線程傳遞數據給另1個線程
    • 在1個線程中執行完特定任務後,轉到另1個線程繼續執行任務
  • 線程間通信常用方法
    - (void)performSelectorOnMainThread:(SEL)aSelector withObject:(id)arg waitUntilDone:(BOOL)wait;
    - (void)performSelector:(SEL)aSelector onThread:(NSThread *)thr withObject:(id)arg waitUntilDone:(BOOL)wait;

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章