thinkphp並發 阻塞模式與非阻塞模式


結構代碼

public function index(){

        $fp = fopen("lock.txt", "w+");
        if(flock($fp,LOCK_EX))   
        {
            // 處理商品數據
          
            flock($fp,LOCK_UN);
        }
        fclose($fp);
    }

概述:

1.首先,讀寫方式打開或者創建文件lock.txt文件

2.給lock.txt文件上 "獨占鎖",上鎖成功后就可以進行下一步"處理訂單商品數據了"

3.處理完數據后,要"釋放鎖”,以及fclose關閉打開的文件

注意:給文件“獨占鎖”后,如果再沒有里面的“釋放鎖”,就沒有下一個"輪回" 

 

fopen詳細介紹:http://www.w3school.com.cn/php/func_filesystem_fopen.asp

flock詳細介紹:http://www.w3school.com.cn/php/func_filesystem_flock.asp

fclose詳細介紹:http://www.w3school.com.cn/php/func_filesystem_fclose.asp

 

詳細代碼

namespace app\index\controller;
use think\Controller;
use think\Cache;

class Index extends Controller
{
   
    /**
     * 首頁
     * */
    public function index(){

        $fp = fopen("lock.txt", "w+");
        if(flock($fp,LOCK_EX))   //鎖定當前指針,,,
        {
            //..處理訂單

            $stock = $this->findStock();
            if($stock > 0){
                $this->setDec();
            }else{
                return '搶購失敗';
            }
            return $stock;
            flock($fp,LOCK_UN);
        }
        fclose($fp);
    }

    /**
     * 查詢數據庫庫存
     * */
    public function findStock(){
        $res = db('info')->where('id',1)->field('stock')->lock(true)->find();
        return $res['stock'];
    }

    /**
     * 減少庫存操作
     * */
    public function setDec(){
        $res = db('info')->where('id',1)->setDec('stock',1);
        return $res;
    }
}

 

總結有點:

1.可以解決並發問題,庫存為負數的情況。

2.並發是,大家都在等待。當所有並發結束后,才會獲得跳轉(這也是缺點,如果處理1000條並發,需要時間15s,那么所有參加的人都需要等待15s后才進入下一個頁面)

 

非阻塞模式

結構代碼,與阻塞模式不同的地方 LOCK_NB (如果不希望 flock() 在鎖定時堵塞,則給 lock 加上 LOCK_NB)

代碼:

 public function index(){
        $fp = fopen("lock.txt", "w+");
        if(flock($fp,LOCK_EX | LOCK_NB))
        {
            $stock = $this->findStock();
            if($stock > 0){
                $this->setDec();
            }else{
                return '搶購失敗';
            }
            $this->setDec();
            return $stock;
            flock($fp,LOCK_UN);
        }
        else
        {
            echo "搶購失敗,要不再試試";
        }

        fclose($fp);
    }

 

總結:

1.相比阻塞模式的時間等待,非阻塞模式則更加人性化很多

2.如果有有很多人都進入搶購,人太多就會直接進入第二個動作(“搶購失敗界面”)。部分人就會進入第一個動作(“搶購候選名單”), 下一個步驟1.搶購成功 或者2 搶購失敗

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM