<dl id="wqg5j"></dl>

    1. <menuitem id="wqg5j"></menuitem>

      <dl id="wqg5j"><font id="wqg5j"></font></dl>
    2. <dl id="wqg5j"><ins id="wqg5j"></ins></dl>
    3. <dl id="wqg5j"><ins id="wqg5j"><thead id="wqg5j"></thead></ins></dl>
      <li id="wqg5j"><ins id="wqg5j"></ins></li>
      安基網 首頁 編程 軟件學院 查看內容

      為何游戲服務端用 C++ 來寫,是歷史原因還是性能方面的考慮?

      2018-10-9 02:04| 投稿: xiaotiger |來自: 互聯網


      免責聲明:本站系公益性非盈利IT技術普及網,本文由投稿者轉載自互聯網的公開文章,文末均已注明出處,其內容和圖片版權歸原網站或作者所有,文中所述不代表本站觀點,若有無意侵權或轉載不當之處請從網站右下角聯系我們處理,謝謝合作!

      摘要: 游戲也分不同領域,不同的游戲之間業務邏輯和適用架構區別很大,并不能一概而論。比如對于大部分手游、頁游來說,追求短平快的開發節奏也不要求太高的實時性和計算效率,C++在這些領域的使用屬于殺雞用牛刀。國內這 ...

      游戲也分不同領域,不同的游戲之間業務邏輯和適用架構區別很大,并不能一概而論。

      比如對于大部分手游、頁游來說,追求短平快的開發節奏也不要求太高的實時性和計算效率,C++在這些領域的使用屬于殺雞用牛刀。國內這些領域還采用 C++ 的團隊,要么是技術決策者視野狹窄;要么是大廠成熟團隊已有完善的遺留技術棧、工具鏈和人才儲備,遷移到其他語言的收益相對不高,或是怕擔轉型決策風險等等;再有就是從大廠出去創業順走了技術框架或迷信大廠經驗的團隊等。

      題主特別提到 MMORPG ,此處就 MMORPG 這一領域為何普遍使用 C++ 進行簡單討論。

      MMORPG主要是指在地圖上實時戰斗一類(比如 WOW、傳奇等),不包括回合制 MMORPG (神仙道、夢幻西游等)。

      常見 MMORPG 服務器在技術層面的特性需求:

      • 網絡IO密集。高頻率的視野同步消息(一般在 10-60Hz 之間),與玩家數量的關系是 O(n^2) 的復雜度,對于一些側重國戰等玩法的 MMORPG 尤其壓力山大。通常都需要配合相關視野管理算法來減少消息發包數量,甚至需要配合架構做廣播的負載分流。
      • CPU密集。MMORPG 的玩法規則都需要服務器做權威性的計算,簡單些的也需要大量怪物的 AI 和尋路計算,以及實時戰斗的邏輯和技能運算等等;一些先進的 3D MMORPG 服務器甚至整合了物理引擎,來做碰撞檢測和校驗。
      • 實時性。此類游戲側重實時戰斗和交互體驗,能容忍的響應延遲通常在 200ms 以內,即使可以通過客戶端預演算進行緩和。考慮到網絡延遲這個不能通過語言和架構來解決的要素,兩次游戲邏輯更新發包的間隔最好控制在幾十毫秒這一量級。(所以一些 GC 不太注重實時性的語言,可能會有潛在的負面體驗影響)。
      • 穩定性和容災。常 Crash 的服務器,輕則影響玩家體驗,重則導致公司倒閉。
      • 開發效率。這個方面除了受語言特性本身影響,還需要考量其它要素,比如生態圈豐富程度(需要的功能可以容易找到穩定好用的庫)、周邊工具鏈完善程度、人員補充難易程度(是否是學校培訓的主力語言、是否是領域比較主流的語言,或者是否足夠簡單好培訓)、現有遺留人力和技術資源的價值等等。

      C++ 和其它候選語言的比較

      C++:

      • 網絡 IO:歷史上這方面曾經是考量的主要因素,近年來幾乎所有主流后端語言都封裝有高效的網絡 IO 庫,C++ 已不具備獨特優勢。
      • CPU 利用率:C++ 在這方面的優勢不需要討論了吧...
      • 實時性:無 GC,內存分配延遲可控(內存池、預分配等),毫秒級延遲需求的高頻交易都在用。
      • 穩定性和容災:用 C++ 寫出長期穩定運行的服務器程序,對開發團隊而言是件要求比較高的事情,尤其在邏輯復雜又變更頻繁的前提下。語言本身也不保證內存訪問的安全性,如果有內存寫越界導致的 Crash 也很難定位。國內某大廠采用了分離數據和邏輯進程,通過進程間共享內存來通信的方式,來實現邏輯進程崩潰重啟不丟失數據。不過這種做法有一定門檻,存在性能開銷,而且對開發效率和靈活性也有比較大的約束,也不易整合第三方庫,不能算是通用的最佳實踐。
      • 開發效率:如果有良好的內力和 C++ 編程素養,并且配合現代 C++ 的一些語法(auto、lambda、智能指針等),開發效率尚可算是勉強及格,但相對以下討論的其他語言來說仍處于劣勢,然而達到上述水準的人力資源成本卻要比其它語言要高出不少(人員補充速度、培訓周期和薪資)。綜合而言,這方面可算 C++ 的一大短板。

      那么,假設不采用混合語言的方案(C++ 配合 Lua 或 Python,或者多服架構不同服務器用不通語言 等),除了 C++ 之外還有哪些語言值得考慮?

      考慮到 MMORPG 在 CPU 計算方面的壓力,解釋型語言暫且可以排除。

      目前考察過的備選方案,主要有 Java、C#、Go、Rust。

      Java:

      優點:

      • 生態圈成熟,庫豐富。
      • Netty 網絡庫性能強悍。
      • 不爽語法還可以用 scala 和 kotlin...

      缺點:

      • 除了原始類型外,不支持自定義值類型。而且泛型是以類型擦除的方式實現。這樣的特性導致了:1.難以把數據連續緊湊地進行表示來優化算法的緩存命中率,比如2D地圖的每個格子坐標都是個object,尋路算法呵呵。3D 場景的碰撞體每個頂點都是個object,物理引擎呵呵。2.對原本對實時性不甚友好的 GC 造成了更大壓力。
      • 成熟的 JVM 實現并不怎么側重 GC 的實時性。如果觸發了百毫秒以上的世界凍結 GC 延遲,所有在線玩家都會受到影響。
      • JIT 在預熱不足的情況下,偶爾會導致性能曲線不平滑,引入預料之外的響應延遲。

      C#:

      優點:

      • 開發友好,語法糖甜。
      • 有真正的泛型和值類型。特定算法好優化。

      缺點:

      • 微軟家的。微軟家的。微軟家的。跑在 Windows Server 下沒什么問題,然而拋開授權費不談,大部分主流的開源好物都是優先考慮 Unix / Linux,比如 Redis(長期沒有 Windows 版本的官方支持)、MongoDB(Windows 下性能要弱于 Linux 下),而且 Windows Server 的網絡性能也要弱一些。除非解決方案都用微軟全家桶,不然部署和運維就需要同時維護兩個平臺...至于 Mono,跟 JVM 比起來就像玩具。只能期待 Rosalyn 成熟了。(目前項目正在用 .Net Core,實現游戲邏輯跑在Linux下問題不大,一些跟操作系統聯系比較緊密的底層功能還是用了C++)
      • GC 實時性類似 Java。

      Go:

      優點:

      • 語法簡單易掌握。
      • 開發體驗友好。
      • 有值類型。
      • 新版本的 Go,GC 實時性良好(1.8 號稱 STW 控制在 1ms 以內)。

      缺點:

      • 沒有范型,某些地方需要轉型成 interface{},不過編譯器會做逃逸分析,不必要的地方不會自動 boxing,影響不算太嚴重。

      Rust:

      優點:

      • 運行效率比肩 C++。
      • 語言特性優秀。
      • 編譯期保證了內存安全,沒有 GC 開銷。
      • 編譯期保證線程安全,可以放心大膽地并發,容易寫出高效的多線程代碼(不過死鎖是需要自己避免的)。

      缺點:

      • 上手曲線較陡。
      • 太年輕,生態圈尚未成熟。
      • 較小眾,人員補充困難。

      大部分 MMORPG 主要采用 C++ 并不是沒有原因 ,雖然歷史原因的比重不小。然而如果要在什么都沒有的情況下,從零開始開發 MMORPG 服務器,采用 C++ 并無必要。拋開人才儲備的方面不談,Go 算是目前開發 MMORPG 服務器各方面特性都比較匹配的選擇:無論開發效率還是運行效率,以及工具和人員培訓速度等等。如果是技術導向的團隊,可以試試 Rust。C# 和 Java 也是不錯的選擇,雖然有些特性不是很好滿足,但也足夠支撐一款游戲成功了(如果不追求提供極致的平滑體驗的話)。

      至于 C++,在具備一些前提條件的情況下可以考慮采用:已有成熟 C++ MMORPG 代碼框架;已有 C++ 寫得 666 的技術團隊;不差錢也不趕進度,就要質量稍高一些的流暢體驗;需要整合一些 C++ 庫等。不過即使如此,C++ 也推薦搭配其它語言使用(比如早幾年常見搭配 Lua,主要用來提高迭代速度和開發效率,并且一定程度上可以支持熱更)。

      目前幾乎沒有純粹的 C/C++開發游戲服務端的。

      早年開發游戲必須用C++,這沒得說,2000-2004年,java還沒有nio,其他動態語言不抗重負,只能C/C++能開發出完整可用的游戲服務端。直到2005年,韓國的游戲很多都還是純C++寫服務端,金山之前也開發過很多純粹C++的游戲服務端,后來大家都切了。

      現代選擇有很多:java + javascript, c+python, c+lua, scala, go, erlang。面向性能的服務器用 java,面向邏輯服務器 python,面向高并發的會選擇 scala,次一級高并發或者性能測試程序(機器人)會選擇 gevent。那是不是就不用C++呢?用 C來做網絡,不用C++,但是C的比例在所有代碼中占比有限。

      這是否意味可以放棄C/C++了?也不是:C語言是一把鋒利的匕首,而現代動態語言是一把長劍。平時匕首可以藏在身上,大部分時候用長劍披荊斬棘就夠了,但當碰到堅硬的石頭,長劍不管用了,那么拿出匕首來果斷的切碎他。

      對于一個成熟領域而言,建議是盡量用更高級一點的開發語言,因為游戲開發很多核心技術都有了較為妥當的解決方法。大量的服務端邏輯其實都是在等待,等待網絡,等待數據庫,這種情況下用C得不償失。但是服務端有一些地方還是躲不開C/C++,比如當服務器涉及到 3D計算的話(國內很多2D服務端,國外很多3D服務端),大量的矢量矩陣,除了用C++封裝出一套好用的數學庫外,即便直接用java寫,那也是很麻煩的。再比如現在快速動作越來越多,為了讓玩家操作更流暢,需要基于 UDP快速可靠協議,協議開發用 java或者scala,性能上是沒辦法滿足要求的,況且協議實現后要和客戶端通信,沒法讓所有客戶端跟著一起用java/scala。再比如某些cpu密集的抽象度高的模塊,如 aoi或者 ai模塊。

      對于一個新興領域而言,C/C++很多情況下是別無選擇的東西。比如移動化浪潮剛起步的時候,還沒有啥 cocos或者 unity真要開發游戲,必須迅速的使用起 OpenGL ES和 OpenSL,然后再疊加某一腳本,以快制勝,第一批移動浪潮上發財的就是這些游戲。又或者,可以根本躲開,先不介入,等到幾年后cocos和 unity成熟了,在介入用lua / C#寫程序。再比如服務端如果離開熟悉的游戲和web,去開發一個陌生的領域,如流媒體服務,會發現這怎么和10年前的游戲一樣呀,什么高級工具都不給用用,這時可以再等個四五年應該高級工具會出現,異或想領先別人時,就果斷的拿出 C/C++來解決之,這就是C獨有的開拓新領域能力。

      大部分答案都是非黑即白,非此即彼。不要只會C不會動態語言,避免成為一個傻逼;也不要只會動態語言不會C,避免離開熟悉的溫室就活不下去。對于一個新手而言,如果什么都沒學過,建議是先用快速開發的東西,把項目弄起來再說,有精力有機會的情況下,也不能完全放棄一些基礎的東西,讓自己殘缺了。

      PS:在相同架構下,就純粹性能而言,各種語言性能差距到底是多少呢?如果只開發回合制這些慢節奏游戲,或者HTTP接口,大部分情況都在等待數據庫等待用戶消息的話,差別確實不大,的確可能5%都不到。如果cpu密集了,那么可以參考下面的圖表,總體來說是10-50倍的性能差別:

      有人問,說了半天,這個也不行,那個也不完美,而時間有限,有沒有一個更經濟實惠的方法呀?如何才一次性達到彼岸呀?時間有限項目吃緊有沒有更好的選擇?說有!那就是 java。國內游戲開發繞來繞去還是腳本+C+erlang+go,難道大家就不會其他東西了么?大部分可以的情況下,除了非用C/C++,推薦各位認真考慮下 java,這個性能上最接近C的東西,能承當大部分cpu密集型事務,卻又不會象c那樣 crash了找都找不到問題在哪里。同時面向高并發時基于原生jvm的 scala可以提供類似 erlang的簡單方式,函數式編程 & 大規模并發協程 & actor;同時 java可以很方便的同 javascript結合,js的速度應該是動態語言里面最快的吧。再者 java還有 groovy,可以提供 python/ruby的泛型編程,用超高的開發效率和 python/ruby媲美,同時還能和 scala 結合實現高并發。最重要的是寫 java好招聘,到處都是寫 java的工程師,大部分語言級的培訓都可以省略了。

      國內游戲開發者很多拒絕學習 java,因為很多開發者自己是碰都沒碰過。現在拒絕 java的人,大部分只是在游戲圈子里面打轉的人,偶爾開發下 web,缺乏其他行業和領域的經驗。看看除游戲外,當今多少世界級的開源服務器是用 java開發的?游戲就真有那么特殊么?看不是,國外大把java開發的游戲服務端,各位如果知道游戲服務端領域有啥 java技術棧解決不了的事情,麻煩告訴一聲。再看看java上下游的 scala, javascript, groovy這些東西。所以建議各位,有空有條件的情況下,認真考慮下 java技術棧,世界很大,不是只有游戲;即便游戲,現在的開發方法真的對嗎?


      Tag標簽:

      小編推薦:欲學習電腦技術、系統維護、網絡管理、編程開發和安全攻防等高端IT技術,請 點擊這里 注冊賬號,公開課頻道價值萬元IT培訓教程免費學,讓您少走彎路、事半功倍,好工作升職加薪!

      本文出自:https://www.toutiao.com/a6609875045038686728/

      免責聲明:本站系公益性非盈利IT技術普及網,本文由投稿者轉載自互聯網的公開文章,文末均已注明出處,其內容和圖片版權歸原網站或作者所有,文中所述不代表本站觀點,若有無意侵權或轉載不當之處請從網站右下角聯系我們處理,謝謝合作!


      鮮花

      握手

      雷人

      路過

      雞蛋

      相關閱讀

      最新評論

       最新
      返回頂部
      玄机图
      <dl id="wqg5j"></dl>

        1. <menuitem id="wqg5j"></menuitem>

          <dl id="wqg5j"><font id="wqg5j"></font></dl>
        2. <dl id="wqg5j"><ins id="wqg5j"></ins></dl>
        3. <dl id="wqg5j"><ins id="wqg5j"><thead id="wqg5j"></thead></ins></dl>
          <li id="wqg5j"><ins id="wqg5j"></ins></li>
          <dl id="wqg5j"></dl>

            1. <menuitem id="wqg5j"></menuitem>

              <dl id="wqg5j"><font id="wqg5j"></font></dl>
            2. <dl id="wqg5j"><ins id="wqg5j"></ins></dl>
            3. <dl id="wqg5j"><ins id="wqg5j"><thead id="wqg5j"></thead></ins></dl>
              <li id="wqg5j"><ins id="wqg5j"></ins></li>