跳到主要內容

Chloe Procedure 使用

在開發好友系統時, 做了個功能叫做推薦名單, 也就是將最近對戰的玩家記錄到數據表上, 再推給客戶端, 但在獲取數據時發現必須過濾掉已經添加的清單, 索性在表格上添加了一個字段來紀錄是否有效


後來發現Chloe處理這段很麻煩, 沒查到官方有 replace 的功能, 所以自己用了 procedure 來處理, 有點久沒用研究了下 Chole 怎麼調用

官方文檔說明


兩個寫法不一樣, dbContext.SqlQuery<Person> 是直接獲取 Procedure 返回數據的, 就譬如 procedure 最後面寫了 select * from user limit 1; 可以透過這個方式獲取返回的 user 資料, 而 ExecuteNonQuery("Proc_GetPersonName", CommandType.StoredProcedure, id, outputName) 則是透過 Procedure 的 out 獲取數據

我們在更新 recent 表格同時也要獲取 recent 數據, 作法如果

DbParam iUserId = new DbParam("@iUserId", userId); DbParam iRUserId = new DbParam("@iRUserId", recentUserId); DbParam iState = new DbParam("@iState", 1); dbContext.SqlQuery<Tbl_Recent>("proc_update_recent", CommandType.StoredProcedure, iUserId, iRUserId, iState);

這是一個沒有 return 的 procedure 調用方式, Procedure 如下

CREATE DEFINER=`root`@`127.0.0.1` PROCEDURE `proc_update_recent`( IN `iUserId` int, IN `iRUserId` int, IN `iState` int) BEGIN DECLARE ts long; set ts = (UNIX_TIMESTAMP() * 1000) + (MICROSECOND(NOW(3)) / 1000); REPLACE into `recent`(`UserId` ,`RUserId`, `State`) value (iUserId, iRUserId, iState); END


另外得益於使用 Procedure , 在發送邀請功能上需要判斷很多情況, 如果在 c# 處理邏輯就會很繁瑣, 後來使用 Procedure 解決, 如下

CREATE DEFINER=`root`@`127.0.0.1` PROCEDURE `proc_check_send_friendApply`( IN `iApplyUserId` BIGINT, IN `iApplyUserName` VARCHAR(64), IN `iApplyUserHead` VARCHAR(128), IN `iToUserId` BIGINT, OUT `oData` INT) MAINLOOP:BEGIN # declare timestamp DECLARE ts BIGINT(20) default 0; DECLARE isMyFriend TINYINT(4) default 0; DECLARE findRecent TINYINT(4) default 0; DECLARE findFriend TINYINT(4) default 0; DECLARE findApply TINYINT(4) default 0; set ts = (UNIX_TIMESTAMP() * 1000) + (MICROSECOND(NOW(3)) / 1000); #已經是我的好友, 退出流程 select count(*) into isMyFriend from `friend` where `UserId`=iApplyUserId and `FUserId`=iToUserId; if isMyFriend != 0 then LEAVE MAINLOOP; end if; #if 如果Recent裡面有數據, 就改掉 state = 1 select count(*) into findRecent from `recent` where `UserId`=iApplyUserId and `RUserId`=iToUserId; if findRecent != 0 then REPLACE into `recent`(`UserId` ,`RUserId`,`State`) value (iApplyUserId, iToUserId, 1); end IF; #if 對方已經是好友就直接加回去, select count(*) into findFriend from `friend` where `UserId`=iToUserId and `FUserId`=iApplyUserId; if findFriend != 0 then REPLACE into `friend`(`UserId` ,`FUserId`,`CreateTime`, `UpdateTime`) value (iApplyUserId, iToUserId, ts, ts); set oData = 2; LEAVE MAINLOOP; end if; #如果沒有邀請過就發邀請 select count(*) into findApply from `friendapply` where `ApplyUserId`=iApplyUserId and `ToUserId`=iToUserId; if findApply = 0 then REPLACE into `friendapply`(`ApplyUserId` ,`ApplyUserName`, `ApplyUserHead`, `ToUserId`, `State`, `CreateTime`, `UpdateTime`) value (iApplyUserId, iApplyUserName, iApplyUserHead, iToUserId, 0, ts, 0); select * from `friendapply` where `ApplyUserId`=iApplyUserId and `ToUserId`=iToUserId limit 1; set oData = 1; end if; END

很久以前在做第一版的麻將時發現那位服務端非常喜歡用存儲過程, 可能是因為服務端 nodejs 且沒有做數據持久化的緣故, 很多數據無法獲取必須重新拉數據, 這樣就會造成數據庫壓力很大, 最早接手開發RPG遊戲時必然是必須做數據持久化的, 設計到服務端乘載人數跟架構, 不做數據持久化管理壓力會壓在Mysql上, 後來做博奕遊戲就很少做這塊了, 輕便為主


留言

這個網誌中的熱門文章

comfyUI 運行出錯 FATAL: kernel fmha_cutlassF_f32_aligned_64x64_rf_sm80 is for sm80-sm100, but was built for sm37

在公司的圖形機器上運行 ComfyUI + WAN 時出現下面問題   FATAL: kernel fmha_cutlassF_f32_aligned_64x64_rf_sm80 is for sm80-sm100, but was built for sm37 算圖機使用的 torch 版本如下 torch 2.7.1+cu118 torchaudio 2.7.1+cu118 torchsde 0.2.6 torchvision 0.22.1+cu118 檢查 cuda 版本 GeForce RTX 5090 CUDA Version: 13.0 從官網看 RTX 5090 支持 12.0 版本 CUDA 這是因爲本地的 pytorch 版本太舊 到官網查詢版本 https://pytorch.org/get-started/locally/ $ pip3 install torch torchvision --index-url https://download.pytorch.org/whl/cu126 查詢目前版本 $ pip list | findstr torch 使用這個版本后出現下面問題 後面查詢 no kernel image 問題其實還是 pytorch 並不支持 sm_120( Blackwell架構) 查看后發現并沒有支持 sm_120 CUDA architectures : [' sm_37 ', 'sm_50', 'sm_60', 'sm_61', 'sm_70', 'sm_75', 'sm_80', 'sm_86', 'sm_90', 'compute_37'] sm_50, sm_52, sm_53 : Maxwell (GTX 900 系列) sm_60, sm_61, sm_62 : Pascal (GTX 1000, P100) sm_70, sm_72, sm_75 : Volta/Turing (V100, RTX ...
仔細回想最近的作的 stripping level,還是回頭來說說 import dll 這回事吧;因為從事遊戲改版所以很多事情是言不由衷的,某天發現 server 發送給 client 封包是 big5 encode,第一時間覺得為何不用 unicode 呢?但仔細想也許是遊戲剛規劃時 DB 都已經存了 big5 編碼字串可能已經改不動了,想想也是就算了,結果一包到 android 就發生了 GetEncoding error,因為 android 是採用 unicode 編碼的,在網路上找了找終於找到解法,可以參考底下網址的討論串,主要是下載  I18N.dll、I18N.CJK.dll、I18N.West.dll 並丟到 Assets 資料夾下就可以了,當時還不是很了解為什麼只知道把 dll 都丟進去在手機上就可以跑,直到使用 stripping level 後整個又掛了,才認真去 trace, 問題在於勾選 strip asm 包檔後 I18N.CJK 就沒被包到 apk 裡面,而要解決 strip asm(~"~ 沒辦法 strip asm 很吸引我,一定要想辦法克服)採用了 link.xml 的方式,但這樣要怎麼知道弄進哪些 lib 呢?

unity 在 STANDALONE 下的解析度問題集合

目前常規的PC游戲顯示模式有幾種模式如下, 一、視窗模式( FullScreenMode. Windowed) 二、獨占模式( FullScreenMode. ExclusiveFullScreen ) FPS游戲多數使用獨占模式,也是最早的全屏幕模式,性能較好,但使用 Alt+Tab 時切換會出現閃頻 三、無邊框模式 ( FullScreenMode. FullScreenWindow ) 目前游戲多數使用這個模式,開啓後切換不會出現閃屏 問題1、切換解析度時屏幕出現黑屏無訊號 Exclusive Fullscreen 必須使用顯示卡的「原生支援模式」( Display Modes ),Windows 桌面「縮放 / 插值後」能顯示許多非原生模式,但 Unity 的 Exclusive Fullscreen 只能切換到顯示卡真正支援的模式 ,不能靠 OS 自動補正。 如果顯示卡沒有 真正的 1280×800 模式: Windows 桌面會用 GPU scaling → 顯示正常 Unity Exclusive Fullscreen 嘗試切換 → 找不到完全匹配的 mode → 會改用 fallback (通常 1280×720 或 native resolution ) 結果畫面偏移、拉伸或出現 左側黑屏 所以: 你以為進入了 1280×800,但實際上顯卡沒有成功切換到這個 mode。 問題2、兩個屏幕,一個 1080p,一個2k,切換2k解析度時出現錯誤,游戲無法調整到對應的2k解析度 目前沒有處理這個問題。 問題3、無邊框模式切換獨占模式無效 在主要解析度,譬如設備解析度為 1920 X 1080 ,情況下從無邊框模式切換到獨占模式,雖然切換成功,但實際上卻是無邊框模式,這是 windows 全螢幕最佳化處理的結果, unity 無法干涉。 原因是  Windows 10/11 強制 Fullscreen Optimizations (全螢幕最佳化),導致獨占模式被轉成 Borderless Fullscreen Windows 會把要求 Exclusive Fullscreen 的遊戲「包裝成」 ➡ Borderless Fullscreen + 可變刷新率 + 全螢幕優化圖層 這樣能快速切換視窗、疊加 U...