3 điểm bởi GN⁺ 2026-02-09 | 1 bình luận | Chia sẻ qua WhatsApp
  • Tôi phát triển mọi trò chơi trong dự án cá nhân bằng ‘C thuần’, một lựa chọn hiện nay khá hiếm
  • Tiêu chí cốt lõi khi chọn ngôn ngữ là độ tin cậy, tính di động và khả năng duy trì lâu dài, không bị ràng buộc vào một hệ điều hành hay nền tảng cụ thể nào
  • Tôi coi trọng sự đơn giản và tốc độ biên dịch nhanh, cùng với kiểm tra kiểu nghiêm ngặt và hệ thống cảnh báo mạnh mẽ
  • Tôi đã cân nhắc các ngôn ngữ thay thế như C++·C#·Java·Go·Haxe, nhưng kết luận rằng chúng không phù hợp vì độ phức tạp, GC, sự áp đặt của OOP, v.v.
  • C nguy hiểm nhưng đơn giản và nhanh, và nhờ khả năng hỗ trợ nền tảng rộng cùng hệ sinh thái thư viện vững chắc, nó vẫn là lựa chọn tối ưu

Tiêu chí chọn ngôn ngữ

  • Điều kiện bắt buộc là độ tin cậy và sự ổn định, để tôi không phải lãng phí thời gian vào những lỗi mà mình không tạo ra
    • Trước đây tôi từng phát triển game dựa trên Flash, nhưng do Flash suy tàn, tôi muốn tập trung làm game mới thay vì chuyển chúng sang nền tảng mới
    • Tôi coi trọng tính di động và hỗ trợ thư viện phổ dụng để không bị phụ thuộc vào một hệ điều hành cụ thể và vẫn mở ra khả năng phát triển cho console
  • Những điều kiện mong muốn bao gồm cú pháp đơn giản và cấu trúc dễ nhớ
    • Tôi muốn tránh việc liên tục phải tra cứu các API hay tính năng ngôn ngữ phức tạp
  • Tôi muốn giảm lỗi bằng kiểm tra kiểu nghiêm ngặt, cảnh báo mạnh và phân tích tĩnh, đồng thời dễ tìm vấn đề hơn nhờ trình gỡ lỗi tốt và các công cụ phân tích động
  • Tôi đánh giá tốc độ biên dịch là cực kỳ quan trọng
    • Thời gian chờ dài làm đứt mạch tập trung và giảm năng suất
  • Tôi hoài nghi về lập trình hướng đối tượng (OOP), và thích cách tách dữ liệu với mã để xử lý tùy theo tình huống hơn

Đánh giá các ngôn ngữ thay thế chính

  • C++
    • Dù vẫn là tiêu chuẩn trong phát triển game, tôi không hài lòng vì độ phức tạp và tốc độ biên dịch chậm
    • Nó mang lại hiệu năng cao và nhiều tính năng, nhưng cũng có quá nhiều tính năng tôi không muốn và cái giá phải trả cho độ phức tạp là rất lớn
  • C# và Java
    • Chúng dài dòng và phức tạp, đồng thời giảm mức độ tự do vì cấu trúc quá nặng về OOP
    • Là ngôn ngữ bậc cao, chúng che giấu độ phức tạp, nhưng không ngăn được các vấn đề cốt lõi
  • Go
    • Tôi đánh giá tích cực nó như một bản diễn giải hiện đại của C, nhưng garbage collection stop-the-world không phù hợp với phát triển game
    • Ngoài ra còn có lo ngại về sự thiếu hụt thư viện cho game và tính bền vững lâu dài
  • JavaScript
    • Những thay đổi nhanh trong môi trường phát triển web và cái kết của Flash khiến nó tạo cảm giác thiếu ổn định
    • Tôi cho rằng cú pháp lỏng lẻo khiến nó không phù hợp để viết phần mềm quy mô lớn
  • Haxe
    • Tôi đánh giá nó đầy hứa hẹn khi phát triển web, nhưng vẫn lo ngại về tính bền vững vì đây là một ngôn ngữ còn tương đối mới
  • Tự phát triển ngôn ngữ riêng
    • Đây là một ý tưởng hấp dẫn, nhưng tôi cho rằng không thực tế vì phải từ bỏ các thư viện hiện có và gánh nặng duy trì khả năng tương thích

Vì sao chọn C

  • Đây là một ngôn ngữ nguy hiểm nhưng đáng tin cậy; nhờ cấu trúc đơn giản, nếu dùng cẩn thận thì vẫn rất ổn định
    • Tác giả ví nó như một “con dao sắc”: khó sử dụng nhưng khi đã thành thạo thì là một công cụ rất mạnh
  • Tốc độ biên dịch rất nhanh và có thể chạy trên gần như mọi nền tảng
    • Quá trình port cũng tương đối đơn giản, và về lâu dài khả năng tồn tại của nó cũng cao
  • Hỗ trợ thư viện và tooling rất mạnh, đồng thời vẫn được duy trì ổn định
  • Về cá nhân, tôi đã có nhiều kinh nghiệm với mã ‘C thuần’, nên rất quen thuộc với nó
  • Tôi không khuyến nghị người khác dùng C; đây là một lựa chọn tối ưu cho sở thích cá nhân và cách làm việc của riêng tôi

1 bình luận

 
GN⁺ 2026-02-09
Ý kiến trên Hacker News
  • Tôi chủ yếu viết code theo phong cách C, chỉ dùng tính năng C++ khi thực sự cần
    Vì vậy nhìn thoáng qua đôi khi còn giống code Rust
    Những người nói họ viết game bằng C thường ghét các tính năng của C++, nhưng rồi cuối cùng lại tự triển khai giao diện ảo hoặc viết những khối switch khổng lồ để làm việc tương tự
    Nếu không muốn thì cứ đừng dùng các tính năng có sẵn trong ngôn ngữ, chứ than phiền về việc chúng tồn tại thì tôi thấy không có nhiều ý nghĩa
    C++ không chậm khi biên dịch nếu bạn không lạm dụng template

    • Khi phát triển một mình thì có thể như vậy, nhưng với dự án được duy trì lâu dài bởi cả một nhóm thì lại khác
      Theo thời gian, thành viên thay đổi, leader thay đổi, và tập hợp các tính năng được sử dụng sẽ ngày càng phình ra
      Một khi đã mở rộng thì cực kỳ khó thu gọn lại
      Ngoài ra bạn cũng có thể buộc phải dùng thư viện sử dụng những tính năng mình không muốn
      Ví dụ, tôi ghét các lời gọi ngầm định như destructor hay operator overloading, nhưng nếu thư viện dùng thì cuối cùng mình vẫn phải theo
    • Ít nhất thì switch còn đọc được
      Một trong những điểm tệ nhất của C++ là có quá nhiều đoạn mã ẩn được sinh ra tự động
    • Dynamic dispatch của C++ hoạt động bằng cách gắn vtable vào mọi kiểu
      Dù phần lớn code chỉ xử lý các kiểu cụ thể như Goose hay Duck, mọi object vẫn phải mang theo con trỏ vtable
      Trong khi đó Rust chỉ dùng vtable ở những chỗ thực sự cần, nên tiết kiệm bộ nhớ hơn
      Lập trình viên C thì tự triển khai đúng phần mình cần, nên ít bị trói buộc bởi cấu trúc mà ngôn ngữ áp đặt
    • C++ vẫn chậm ngay cả khi không lạm dụng template
      Chỉ cần include mỗi <vector> thôi cũng kéo theo hàng chục nghìn dòng code
      Vì thế nếu không dùng standard library thì lại nổ ra tranh cãi kiểu “sao phải phát minh lại bánh xe”
      Mà những cuộc tranh cãi như vậy lặp đi lặp lại thì quay về C lại dễ chịu hơn hẳn
      Tôi cũng chuyển sang C từ khoảng năm 2017, và đến giờ cứ mỗi lần dùng thư viện C++ là lại thấy mệt
      Ngoại lệ thì Dear ImGui khá ổn, nhưng ngay cả với nó tôi vẫn thích C binding hơn
    • Tôi từng thực sự viết một file C++ mà không dùng lấy một tính năng C++ nào
      Đổi phần mở rộng sang .c thì thời gian biên dịch giảm một nửa
  • Tôi thích sự thô ráp và đơn giản của C, chỉ là ghét preprocessor
    Vì thế Zig đúng là như món quà trời cho — đơn giản hơn C nhưng lại có thiết kế ngôn ngữ chính xác hơn
    Ví dụ, Zig phân biệt giữa con trỏ đơn và con trỏ mảng
    Có thể import thư viện C rồi biến chúng thành thứ dễ dùng hơn, rất hữu ích trong phát triển game
    Phần lớn thư viện C++ cũng đi kèm header C
    zig-gamedev có rất nhiều thư viện C được Zig hóa như vậy
    Thay vì preprocessor, tính năng comptime của Zig tốt hơn nhiều, và về bản chất nó chỉ là “code Zig chạy ở thời điểm biên dịch”

    • Nhưng thực tế thì số thư viện C++ export ra header C lại quá ít
  • Tôi cũng đồng cảm với quan điểm của tác giả
    Lý do lớn nhất khiến tôi thích một ngôn ngữ là sự đơn giản
    Vì thế tôi ưu tiên những ngôn ngữ như C, Go, Odin và Zig
    Nhưng những ngôn ngữ xử lý độ phức tạp cần thiết một cách thanh lịch cũng rất quan trọng
    Với code mạng cần memory safety, concurrency và các mẫu hàm chức năng, Rust là lựa chọn tự nhiên
    Còn với code đơn giản và nhanh như game indie thì C hay Odin lại rất hợp
    Odin cho cảm giác như kết hợp sự đơn giản của Go với hiệu năng của C nên tôi khuyên dùng
    Làm game với Raylib cũng dễ

    • Thú vị là tôi thường mô tả Zig như điểm nằm giữa Go và C
      Tôi tò mò không biết bạn có nghĩ Odin phù hợp với vị trí đó hơn Zig không
    • Nhân tiện, tên ngôn ngữ là Go, còn golang chỉ là tên miền
  • Bài gốc nói rằng Go thiếu hỗ trợ thư viện game, nhưng đó có vẻ là một bài viết từ khoảng năm 2015
    Giờ có thể tình hình đã khác

    • Wayback Machine có snapshot từ tháng 1 năm 2016
      Ở đó cũng xem được ảnh chụp màn hình các game được tạo hồi ấy
      Ví dụ Knossu có phong cách 3D khá độc đáo
  • Làm game bằng C vào năm 2026 có thể hơi điên rồ, nhưng tôi cũng đang làm vậy
    Chẳng hạn Chrysalis được tôi phát triển bằng C (dùng GLFW3 và FMOD)

    • Tôi đã làm việc với codebase Jedi Academy được 2 năm rồi (C & C++)
      Nó dựa trên idTech3, mà hệ thống combat thì tinh chỉnh đến mức chỉ một thay đổi nhỏ cũng phá hỏng toàn bộ cân bằng
      Thậm chí chỉ thêm một i++ thôi cũng làm lệch timing
      Vì thế chúng tôi vẫn giữ nguyên compiler từ 22 năm trước
      Có các fork đã hiện đại hóa, nhưng chúng làm mất cảm giác nguyên bản
      idTech3 đúng là engine thể hiện tinh túy của C
  • Hàng nghìn game đã được viết bằng C, và các graphics API như OpenGL, Vulkan, DX cũng đều dựa trên C
    Nên chuyện đó chẳng có gì lạ
    Phần lớn game engine cũng được viết bằng C/C++

    • API của Khronos là C, DirectX là COM/WinRT dựa trên C++, còn Metal là sự pha trộn giữa Objective-C và C++
      Console thì khác nhau theo từng thế hệ
    • SDL3 cũng được viết bằng C, và phiên bản mới nhất của Box2D cũng đã được viết lại bằng C
    • DirectX là C++, và đa số game engine cũng là C++
      Khác với lập trình Linux, phát triển game đã xoay quanh C++ hơn 30 năm nay
  • Về cơ bản thì tôi là người rất yêu C
    Tôi đã dùng nó rất ổn suốt hàng chục năm, nhưng khi quản lý code C theo nhóm thì nỗi đau tăng lên rõ rệt
    Ngoài ra tốc độ phát triển cũng chậm hơn so với các ngôn ngữ hiện đại
    Dù vậy, sức hút từ sự đơn giản của nó vẫn còn nguyên

    • Tôi tò mò vì sao codebase C lại đau đớn hơn khi làm việc theo nhóm
      Theo trải nghiệm của tôi thì C còn đỡ đau hơn C++
    • “Nói ít hơn nhưng mang nhiều ý nghĩa hơn” — tức là tính cô đọng mới là cốt lõi
    • Chỉ riêng năm 2025 đã có 2.134 developer tham gia Linux kernel
      Điều đó phần nào làm suy yếu lập luận về giới hạn cộng tác của C
  • Nói rằng “không ai làm game bằng C” là cường điệu
    Giờ nó không còn là dòng chính, nhưng vẫn có rất nhiều người làm game bằng C

    • Những cách nói như “không ai” hay “mọi người” thường không mang nghĩa tuyệt đối
      Bạn chỉ là ngoại lệ, còn câu đó vẫn đúng về mặt thống kê
  • Tôi thích C
    Tôi có thể kiểm soát hoàn toàn quản lý bộ nhớ, và đổi lại là hành vi có thể dự đoán được
    Trong các môi trường yêu cầu cấp phát sẵn như bộ quy tắc MISRA, nó đặc biệt hữu ích
    Nó cũng phù hợp để trực tiếp xử lý exception hay lỗi ở mức phần cứng
    Viết unit test cũng dễ

  • C có rào cản tiếp cận thấp, nhưng kiến thức về quản lý bộ nhớ là bắt buộc
    Là một lập trình viên Java, khi phải nhanh chóng tạo connector trong tình huống chỉ có .h.so, tôi đã chọn C thay vì C++
    Nếu C là một con dao sắc, thì C++ giống như một cột dao đang xoay — lơ là là bị thương
    Chỉ có điều xử lý chuỗi trong C quá đau khổ, đến mức tôi muốn mượn hệ thống string của C++

    • Điểm hay của C++ là nếu không muốn thì bạn không cần dùng những tính năng đó