AI có thể viết code. Nhưng chính code từng tạo nên chúng ta.
· 33 min read · 6584 words · Read in English
Điều gì sẽ xảy ra với nghề lập trình khi chúng ta tự động hóa không chỉ công việc, mà cả những va vấp từng tạo nên một kỹ sư giỏi?
Một thời gian trước, trong bài Lập trình không còn vui nữa?, tôi đã viết về một cảm giác khá lạ: tôi vẫn thích xây dựng phần mềm, nhưng ngày càng ít trực tiếp viết code.
Không phải vì tôi quên lập trình. Mà vì viết code không còn là nút thắt lớn nhất.
Sau đó, trong The Bottleneck Moved to Review, tôi mô tả cách mình làm việc hiện tại: các tác tử AI đảm nhiệm phần lớn khâu triển khai, còn công việc của tôi dịch chuyển sang đặc tả yêu cầu, thiết kế hệ thống, kiểm tra, bảo mật và xác minh kết quả.
Với những công việc tôi mô tả trong hai bài ấy, tôi thấy đây là một bước tiến. Nhưng tôi không xem trải nghiệm đó là bằng chứng rằng AI luôn làm mọi kỹ sư nhanh hơn.
Nhưng gần đây tôi bắt đầu nghĩ mình đã bỏ sót một câu hỏi khó hơn.
Nếu AI viết phần lớn code, chuyện gì xảy ra với người lập trình viên mà trước đây được hình thành trong chính quá trình viết những dòng code đó?
Câu hỏi này trở nên rõ ràng hơn với tôi sau khi đọc những bình luận gần đây của Terence Tao về AI và toán học.
Khi đáp án không phải là toàn bộ giá trị
Trong chuỗi bình luận ngày 3/9/2026, Terence Tao đưa Navier–Stokes ra làm ví dụ cho một nguy cơ khá lạ.
Hãy tưởng tượng một hệ thống AI cực mạnh được cấp lượng tài nguyên tính toán khổng lồ. Nó thử rất nhiều hướng, sửa sai, kiểm tra các trường hợp, cuối cùng tìm được một chứng minh cho một bài toán mở lớn. Chứng minh ấy thậm chí có thể được hình thức hóa bằng Lean và kiểm tra bằng máy.
Bài toán được giải.
Điều tôi rút ra từ lập luận của Tao là một câu hỏi:
Toán học thực sự nhận được bao nhiêu từ quá trình đó?
Trước đó, trong bình luận ngày 22/4/2026, ông đã tách phần giải quyết bài toán của nghiên cứu toán học thành ba công việc vốn thường đi cùng nhau:
- Tạo ra chứng minh: tìm lời giải cho bài toán.
- Kiểm chứng chứng minh: kiểm tra lời giải có thực sự đúng không.
- Tiêu hóa chứng minh: hiểu ý tưởng quan trọng, đặt kết quả vào bối cảnh và rút ra điều có thể áp dụng cho những bài toán khác.
Theo phần tiếp theo trong lập luận của Tao, AI và công cụ hình thức hóa đang tăng tốc hai công việc đầu nhanh hơn quá trình con người hiểu và hấp thụ chứng minh. Đây là nhận định của ông về thực hành toán học, không phải một phép đo chi phí chung cho mọi bài toán.
Tao diễn đạt sự lệch nhịp ấy như một vấn đề của thời đại tạo và kiểm chứng chứng minh nhanh: một kết quả chưa được hiểu, giải thích và đặt vào bối cảnh vẫn chưa phải lời giải trọn vẹn theo tiêu chí ông đề xuất. (Tao, phần 3/3)
Ở đây, tôi dùng kịch bản của Tao như một thí nghiệm tư duy, không phải một kết luận về tình trạng giải quyết bài toán Navier–Stokes. Điều khiến tôi quan tâm là khoảng cách giữa có được một kết quả đúng và hiểu được điều gì mới từ kết quả ấy.
Bởi kỹ nghệ phần mềm có thể đang tiến rất nhanh tới cùng một vấn đề.
Chúng ta từng nghĩ code là sản phẩm
Nếu chỉ nhìn vào đầu ra, ta dễ mô tả lập trình như một chuỗi khá đơn giản:
Có một vấn đề. Lập trình viên suy nghĩ. Lập trình viên viết code. Code chạy. Sản phẩm xuất hiện.
Trong cách nhìn đó, viết code chỉ là một chi phí trung gian.
Nếu máy có thể làm công đoạn này nhanh hơn, việc giao nó cho máy có vẻ hoàn toàn hợp lý.
Nhưng năm 1985, Peter Naur đưa ra một cách nhìn khác trong bài Programming as Theory Building.
Ông lập luận rằng mục tiêu chính của lập trình không đơn thuần là tạo ra chương trình.
Trong quá trình xây dựng phần mềm, lập trình viên đồng thời xây dựng trong đầu mình một lý thuyết về hệ thống:
Vấn đề thực sự là gì? Các thành phần liên hệ với nhau ra sao? Vì sao một quyết định được chọn thay vì quyết định khác? Hệ thống sẽ phản ứng thế nào khi điều kiện thay đổi?
Theo cách nhìn này, mã nguồn chỉ là một phần của kết quả. Phần còn lại nằm trong đầu những người đã xây dựng nó.
Theo cách nhìn của Naur, đọc cùng một kho mã nguồn chưa bảo đảm hai người có cùng khả năng sửa đổi nó. Người đã xây hệ thống có thể nắm những lý do thiết kế mà tài liệu chưa truyền tải được. Tôi hình dung sự khác biệt ấy qua những tình huống như sau:
Không phải vì người đó nhớ từng dòng code.
Họ nhớ lịch sử của những quyết định.
Họ biết lớp trừu tượng này tồn tại vì cách cũ đã thất bại thế nào. Họ biết cơ chế thử lại kia không phải được chọn ngẫu nhiên. Họ nhớ tại sao một mô-đun trông hơi xấu nhưng chưa thể sửa cấu trúc. Họ biết một yêu cầu tưởng như đơn giản nào từng gây ra lỗi tranh chấp dữ liệu. Họ có một lý thuyết về hệ thống.
Naur nhấn mạnh rằng việc truyền lại hiểu biết này cần cả cơ hội làm việc cùng người đã nắm hệ thống, thảo luận những tình huống bất thường và thực hành có hướng dẫn. Chỉ tiếp xúc với mã nguồn và tài liệu là chưa đủ theo lập luận của ông. (Naur, phần “Program Life, Death, and Revival”)
Lập trình từng tạo ra hai thứ
Tôi nghĩ đây là cách đơn giản nhất để diễn đạt điều đang thay đổi.
Từ cách nhìn ấy, tôi muốn gọi tên hai kết quả của việc lập trình:
Phần mềm. Và người kỹ sư phần mềm.
Hãy lấy một tình huống giả định: bạn bắt đầu một dự án khi chưa hiểu đầy đủ vấn đề. Bạn viết phiên bản đầu tiên. Nó chậm. Bạn đo đạc hiệu năng. Con số không giống điều bạn dự đoán. Bạn phát hiện nút thắt thực ra nằm ở việc truyền dữ liệu trong bộ nhớ.
Bạn thay cách biểu diễn dữ liệu. Bộ nhớ giảm nhưng độ trễ ở các trường hợp xấu lại tăng. Bạn thêm cơ chế gom nhiều yêu cầu xử lý cùng lúc. Cách đó lại khiến một loại tải khác tệ hơn. Bạn đọc thêm. Bạn thử lại.
Giả sử sau ba tuần thử và đối chiếu kết quả, hệ thống tốt hơn. Điều tôi mong đợi không chỉ là phần mềm chạy nhanh hơn, mà cả mô hình trong đầu người làm cũng chính xác hơn.
Lần sau gặp một vấn đề tương tự, bạn có thể nhận ra khả năng nghẽn bộ nhớ sớm hơn. Tôi gọi việc nhìn thấy một nhóm vấn đề có chung bản chất, thay vì chỉ một lỗi cụ thể, là một phần của khả năng phán đoán mà mình muốn giữ lại.
Phần mềm là sản phẩm hữu hình.
Khả năng phán đoán là sản phẩm vô hình của quá trình làm phần mềm.
Việc thực hành tạo cơ hội học, nhưng không tự động bảo đảm người làm sẽ hiểu sâu. Điểm tôi muốn nối từ Naur sang các nghiên cứu dưới đây là: hoàn thành phần mềm và hình thành hiểu biết là hai kết quả cần được xem xét riêng.
Giả sử một tác tử tạo ra hệ thống tốt hơn trong hai giờ so với thứ tôi tự viết trong hai ngày.
Sản lượng phần mềm tăng. Nhưng năng lực của người kỹ sư không nhất thiết tăng theo.
Đó là thay đổi mà tôi nghĩ chúng ta đang đánh giá thấp.
Đây không chỉ là chuyện “học ít hơn”
Tôi từng viết riêng về vấn đề này trong AI Is Making Us Faster Learners and Worse Thinkers at the Same Time.
Trong một số thí nghiệm lập trình, mức độ hoàn thành nhiệm vụ và khả năng giải thích code không tăng cùng nhau. Hai nghiên cứu dưới đây cho phép nói điều đó ở phạm vi hẹp hơn nhiều so với kết luận “AI làm kỹ sư kém đi”.
Trong thử nghiệm công bố tháng 1/2026 của Anthropic, 52 kỹ sư, chủ yếu ở cấp junior, học thư viện Python Trio. Nhóm dùng AI đạt trung bình 50% ở bài kiểm tra ngay sau đó, so với 67% ở nhóm tự viết code: chênh lệch 17 điểm phần trăm. Khoảng cách lớn nhất nằm ở câu hỏi gỡ lỗi. Nhóm AI hoàn thành nhanh hơn một chút, nhưng khác biệt thời gian không có ý nghĩa thống kê.
Những người hỏi về khái niệm hoặc chủ động tìm hiểu lời giải thường đạt điểm tốt hơn nhóm giao phần lớn việc cho AI. Đây là quan sát từ phân tích định tính, chưa chứng minh quan hệ nhân quả. Thử nghiệm cũng chỉ đo hiểu biết tức thời trong một nhiệm vụ học thư viện mới; nó không kết luận năng lực dài hạn của kỹ sư sẽ suy giảm.
Nghiên cứu More Code, Less Understanding?, đăng trên IEEE Transactions on Software Engineering, cho 69 người tham gia làm hai bài lập trình, một bài có AI và một bài không có. Khi dùng AI, mức độ hoàn thành công việc tăng, nhưng khả năng trả lời câu hỏi kỹ thuật về chính code vừa xây giảm. Mẫu gồm cả sinh viên, nhà nghiên cứu và lập trình viên chuyên nghiệp; phép đo này cũng phản ánh hiểu biết ngay sau nhiệm vụ, không phải toàn bộ năng lực kỹ thuật.
Đây là một vấn đề thật.
Nhưng tôi nghĩ nó vẫn chưa phải phần thú vị nhất.
Nếu chỉ nói rằng:
“Dùng AI khiến chúng ta hiểu code ít hơn.”
thì những biện pháp như walkthrough, giải thích code cho đồng đội và ghi lại lý do thiết kế là các hướng can thiệp đáng thử. Storey đề xuất các thực hành này để giảm nợ nhận thức; đó là đề xuất thực hành, chưa phải bằng chứng rằng chúng khắc phục được mọi tác động của AI.
Có một thứ khác khó phục hồi hơn:
những ý tưởng mà chúng ta không bao giờ phát hiện ra vì không còn phải vật lộn với quá trình triển khai.
Những va vấp từng là một cỗ máy khám phá
Hãy tưởng tượng tôi muốn giảm độ trễ cho một máy chủ suy luận.
Tôi có thể giao cho AI:
Hãy phân tích hiệu năng hiện tại, tối ưu cơ chế gom yêu cầu và sử dụng bộ nhớ, giữ độ trễ p99 dưới X, chạy benchmark và triển khai phương án tốt nhất.
Trong ví dụ giả định này, một tác tử đủ mạnh có thể thử nhiều cấu hình, sửa code, chạy benchmark và trả lại những con số như sau:
Thông lượng tăng 41%. Độ trễ p99 giảm 28%. Toàn bộ kiểm thử đều vượt qua.
Đây là một kết quả tuyệt vời.
Nhưng hãy tưởng tượng một phiên bản khác.
Tôi tự bắt đầu từ profiler. Tôi dự đoán phần tính toán là nút thắt. Sai. Việc sao chép dữ liệu trong bộ nhớ mới là vấn đề.
Tôi thay cách biểu diễn dữ liệu. Trong kịch bản này, tôi nhận ra một đánh đổi giữa việc chờ gom lô và độ trễ của từng yêu cầu. Đây là cơ chế có thật: tài liệu dynamic batching của NVIDIA Triton hướng dẫn thử tăng batch size hoặc thời gian chờ để đổi thêm độ trễ lấy thông lượng. Còn việc cấu hình nào phù hợp vẫn phải đo trên tải cụ thể. Giả sử các yêu cầu của tôi có độ dài rất khác nhau, tôi bắt đầu nghĩ về bộ lập lịch.
Rồi một câu hỏi khác xuất hiện:
Liệu bộ lập lịch có nên tự thay đổi chiến lược dựa trên phân bố tải, yêu cầu về độ trễ và mức sử dụng GPU hay không?
Tôi bắt đầu dự án với câu hỏi:
“Làm sao giảm độ trễ?”
Nhưng những va vấp trong quá trình triển khai dẫn tôi tới một câu hỏi khác:
“Liệu chúng ta có thể tạo ra một chiến lược lập lịch tự thích nghi theo tải thực tế và chi phí vận hành hay không?”
Câu hỏi thứ hai có thể trở thành một thư viện. Một bài nghiên cứu. Một sản phẩm. Hoặc đơn giản là một mô hình tư duy tôi sử dụng thêm mười năm.
Điều quan trọng là tôi không biết câu hỏi đó tồn tại khi bắt đầu.
Tôi tìm thấy nó trên đường đi.
Rời ví dụ giả định ấy, tôi đã kể một trải nghiệm liên quan khi làm AnyLearning.
Trong The GPU Was Already There: Four Silent Bugs in On-Device Training, phần lớn phần triển khai mang tính cơ học có thể được Claude Code hỗ trợ rất nhanh.
Nhưng những hiểu biết quan trọng của dự án lại không đến từ việc code được tạo nhanh đến mức nào.
Chúng đến từ việc đo đạc.
Trong những phép đo được ghi lại ở bài AnyLearning, logic chọn thiết bị bỏ qua GPU của Mac; is_bf16_supported() trả về True trên RTX 2070 dù phép toán BF16 chạy bằng mô phỏng; và FP16 chậm hơn FP32 trên máy M1 tôi dùng. Đó là kết quả trên các máy và workload cụ thể của tôi, không phải quy luật cho mọi GPU.
Còn việc GradScaler bỏ qua optimizer.step() khi gradient chứa inf hoặc NaN là hành vi được ghi rõ trong tài liệu PyTorch. “Âm thầm” trong trải nghiệm ấy nghĩa là log của ứng dụng không theo dõi bước bị bỏ qua; bản thân cơ chế này có chủ đích.
Bài AnyLearning ghi lại cách những vấn đề ấy lộ ra qua đo đạc. Với tôi, đó là ví dụ cụ thể cho giá trị của việc tiếp xúc trực tiếp với hành vi hệ thống.
Đó chính là điểm tôi muốn giữ lại.
Một bài toán khó không chỉ có giá trị vì đích đến.
Địa hình mà ta phải đi qua để đến đó tạo ra bản đồ.
Lập trình cũng vậy.
Từ trải nghiệm ấy, tôi rút ra một nguyên tắc cho mình: đừng xem mọi khó khăn trong triển khai là phần thời gian cần xóa đi. Một kết quả profiler trái dự đoán, một lỗi bảo mật hay một yêu cầu không khớp với hành vi người dùng đều có thể là lý do để đặt lại câu hỏi. Đây là cách tôi diễn giải giá trị của thực hành, không phải kết luận rằng chịu nhiều thất bại hơn luôn tạo ra kỹ sư giỏi hơn.
Va vấp không phải lúc nào cũng là lãng phí. Đôi khi chính nó mang theo thông tin.
Giả thuyết tôi muốn đặt ra là: nếu AI xử lý hết những va vấp trước khi con người nhìn thấy chúng, phần mềm có thể tốt hơn trong khi cơ hội khám phá của người làm ít đi. Các nghiên cứu về điểm kiểm tra ở trên chưa đo được sự mất mát này.
Tôi tạm gọi phần thiếu hụt này là nợ khám phá. Đây là cách tôi đặt tên cho một rủi ro, chưa phải một đại lượng đã được đo lường hay một kết luận thực nghiệm.
Để phân biệt, tôi mượn cách chia ba loại nợ của Margaret-Anne Storey trong From Technical Debt to Cognitive and Intent Debt:
Nợ kỹ thuật là phần code khiến những thay đổi trong tương lai trở nên đắt đỏ.
Nợ nhận thức là khoảng cách giữa hệ thống đang tồn tại và mức độ mà đội ngũ thực sự hiểu hệ thống đó.
Nợ ý định xuất hiện khi lý do và mục đích ban đầu của một quyết định không còn được lưu giữ rõ ràng cho cả con người lẫn AI.
Nợ khám phá khác một chút.
Nó là những hiểu biết chúng ta đáng lẽ có thể tạo ra, nhưng không bao giờ xuất hiện vì quá trình tạo sản phẩm đã được tối ưu quá nhanh.
Không giống nợ kỹ thuật, bạn không thể mở hệ thống quản lý công việc và nhìn thấy nó.
Bạn thậm chí không biết mình đang nợ thứ gì.
Nhưng compiler cũng từng “lấy mất” công việc của lập trình viên
Có một phản biện hiển nhiên.
Nếu quá trình vật lộn quan trọng đến vậy, tại sao không viết assembly? Tại sao dùng bộ gom rác? Tại sao dùng cơ sở dữ liệu thay vì tự viết bộ máy lưu trữ? Tại sao dùng PyTorch thay vì tự triển khai phép convolution?
Lập trình đã có nhiều công cụ giúp người dùng không phải tự triển khai mọi tầng. Compiler và cơ sở dữ liệu là hai ví dụ cụ thể.
Đây là phản biện đúng.
Và vì vậy kết luận không thể là:
“Hãy tự viết mọi thứ.”
Tôi nghĩ khác biệt quan trọng nằm giữa trừu tượng hóa phần cơ học và giao luôn quá trình suy luận.
Trong LLVM, bộ phân bổ thanh ghi ánh xạ thanh ghi ảo sang thanh ghi vật lý hoặc vị trí trong bộ nhớ. Người viết chương trình có thể giao công đoạn đó cho compiler.
PostgreSQL cung cấp sẵn B-tree index và write-ahead logging; người viết ứng dụng không phải tự cài đặt những cơ chế này. Dĩ nhiên, họ vẫn cần hiểu các bảo đảm và giới hạn liên quan đến ứng dụng của mình.
Với tác tử, phạm vi ủy quyền có thể bao gồm cả việc chọn bước tiếp theo. Trong mô tả kiến trúc tác tử của Anthropic, mô hình tự điều khiển quy trình, dùng công cụ và điều chỉnh theo phản hồi từ môi trường.
Từ đó, hãy xét một tình huống ủy quyền rộng: nếu tôi giao cả việc chọn kiến trúc, thư viện và mô hình dữ liệu, rồi chỉ đọc diff cuối cùng, tôi sẽ bỏ lỡ các phương án đã bị loại. Đây là rủi ro của cách giao việc ấy, không phải đặc tính bắt buộc của mọi tác tử.
Tức là AI không chỉ rút ngắn quá trình thực thi.
Nó có thể rút ngắn cả quá trình tìm kiếm trong không gian thiết kế.
Theo cách đọc của tôi từ Naur, những lần lựa chọn và sửa đổi ấy là cơ hội để xây dựng hiểu biết về hệ thống.
Đây cũng là lý do việc đặc tả yêu cầu ngày càng trở thành một phần quan trọng trong cách tôi làm việc.
Trong Ask, or It Will Guess: Question-Asking Is the Core Skill of Agentic Work, tôi viết về một kiểu thất bại mình lo ngại: khi yêu cầu mơ hồ, tác tử chọn một cách hiểu rồi bắt đầu xây.
Có bằng chứng gần với mối lo đó: Su và Cardie, 2026, ghi nhận các mô hình được khảo sát thường trả lời trực tiếp thay vì hỏi làm rõ trên bài toán hỏi đáp mơ hồ. Thí nghiệm này đo hỏi đáp với tập mô hình cụ thể, không đo tác tử lập trình trong repository; áp dụng kết quả ấy vào cách giao việc là suy luận của tôi.
Điều đáng sợ không phải là code xấu.
Nó có thể tạo ra một cách triển khai rất tốt dựa trên một giả định mà không ai chủ động lựa chọn.
Trong tình huống đó, tôi lo rằng giao phần triển khai cũng có thể làm mình bỏ lỡ một phần quá trình hình thành hiểu biết.
Chúng ta không chỉ nâng mức trừu tượng.
Chúng ta đang bắt đầu giao cho máy một phần của quá trình ra quyết định từng giúp con người xây dựng mô hình tư duy về hệ thống.
Code dư thừa, sự hiểu biết khan hiếm
Điều này đưa chúng ta tới một phiên bản trong phần mềm của thế giới “dư thừa chứng minh” mà Tao nói tới.
Giả sử chi phí tạo code tiếp tục giảm. Một kỹ sư có thể chạy năm tác tử. Mỗi tác tử có thể thử ba cách triển khai.
Trong kịch bản ấy, CI chạy build và test, phân tích tĩnh tìm các vấn đề trong code, rồi một mô hình khác đọc lại phần thay đổi. Đây là các lớp kiểm tra với phạm vi riêng; vượt qua chúng không tương đương một chứng minh hình thức rằng toàn bộ phần mềm đúng.
Nếu quy trình ấy hoạt động tốt, lượng code được tạo và vượt qua các kiểm tra tự động có thể tăng nhanh hơn khả năng con người đọc và hiểu nó. Đây là kịch bản tôi đang xét, không phải một dự báo đã được xác nhận.
Khi đó, nút thắt tiếp theo không còn là viết code.
Thậm chí không chỉ là kiểm tra code.
Nó là tiêu hóa code.
Tôi dùng phép đối chiếu sau để làm rõ lập luận; hai cột không có nghĩa các phương pháp kiểm chứng là tương đương:
| Toán học | Kỹ nghệ phần mềm |
|---|---|
| Tạo ra chứng minh | Tạo ra cách triển khai |
| Kiểm chứng chứng minh | Test, kiểu dữ liệu, phân tích tĩnh, benchmark |
| Tiêu hóa chứng minh | Xây dựng mô hình tư duy về hệ thống |
| Rút ra kỹ thuật mới | Rút ra lớp trừu tượng hoặc nguyên lý thiết kế |
| Khái quát kết quả | Áp dụng lại cho những hệ thống khác |
| Đưa vào tri thức chung | Kiến trúc, tài liệu, API, thực hành kỹ thuật |
Trong The Bottleneck Moved to Review, tôi lập luận rằng nút thắt của phần mềm do AI tạo ra đang dịch chuyển từ viết sang kiểm tra.
Tôi vẫn nghĩ điều đó đúng.
Nhưng có lẽ việc kiểm tra cũng chỉ là nút thắt trung gian.
Nút thắt dài hạn có thể là:
Con người có thể biến những thứ do máy tạo ra thành tri thức mà chính mình thực sự sở hữu nhanh đến mức nào?
Điều tôi lo là cách giao việc có thể thay đổi trước khi đội ngũ thiết kế được cách học phù hợp với nó.
Vấn đề của kỹ sư mới vào nghề
Đây là phần khiến tôi lo nhất.
Một kỹ sư giàu kinh nghiệm hôm nay có thể nói:
“Đừng phí thời gian viết code lặp lại. Để AI làm đi. Hãy tập trung vào kiến trúc.”
Lời khuyên đó hoàn toàn hợp lý với một người đã có nhiều năm kinh nghiệm.
Nhưng có một vấn đề.
Hãy hình dung một kỹ sư đã dành nhiều năm làm những phần việc triển khai mà giờ họ muốn giao cho AI.
Họ từng thiết kế API sai. Từng tạo lớp trừu tượng sai. Từng gỡ lỗi deadlock. Từng săn lỗi rò rỉ bộ nhớ. Từng đưa lên production một thứ tưởng là đúng nhưng không thể mở rộng. Từng sửa một sự cố mà unit test không bắt được. Từng nhìn một thiết kế rất đẹp trên sơ đồ vỡ vụn khi gặp dữ liệu thật.
Theo cách nhìn về đào tạo của Naur, thực hành có hướng dẫn và thảo luận về hệ thống là một phần của việc hình thành hiểu biết. Những trải nghiệm trên minh họa con đường ấy; tôi không cho rằng ai cũng phải gặp đủ từng loại lỗi mới có khả năng đánh giá kiến trúc.
Vậy nếu kỹ sư mới không còn trải qua những việc đó nữa thì sao?
Ta có một bài toán về quá trình trưởng thành nghề nghiệp.
AI có thể loại bỏ những công việc mà kỹ sư mới thường làm trước khi chúng ta tìm ra một cơ chế khác để biến họ thành kỹ sư giàu kinh nghiệm.
Đây không chỉ là vấn đề của từng cá nhân.
Nó có thể trở thành vấn đề của cả tổ chức.
Hãy xét thêm một kịch bản giả định, không phải dự báo về thị trường lao động: một công ty có năng suất rất cao vào năm 2026 vì các kỹ sư giàu kinh nghiệm dùng tác tử AI hiệu quả.
Nhưng giả sử năm năm sau, công ty phát hiện lớp kỹ sư tiếp theo rất giỏi điều phối AI nhưng chưa từng đủ gần những thất bại thực tế để xây được khả năng phán đoán cần thiết khi hệ thống gặp một tình huống mới.
Trong kịch bản ấy, công ty đã tối ưu việc sản xuất phần mềm nhưng bỏ thiếu đầu tư cho đào tạo. Thử nghiệm Anthropic chỉ cho thấy rủi ro học một kỹ năng mới trong ngắn hạn; khoảng cách năm năm này là câu hỏi tôi đặt ra, chưa phải điều nghiên cứu ấy chứng minh.
Giữ lại những va vấp có giá trị
Tôi không có ý định quay lại cách viết code như năm 2021. Tôi cũng không nghĩ lập trình viên mới nên bị cấm dùng Copilot, Claude Code hay Codex.
Đó chỉ là cố gắng bảo vệ nghề bằng cách giả vờ công nghệ không tồn tại.
Câu hỏi hữu ích hơn là:
Phần khó khăn nào chỉ là công việc lặp lại vô ích, và phần khó khăn nào đang thực sự xây dựng hiểu biết?
Tôi đang dần dùng một nguyên tắc đơn giản:
Dùng AI để loại bỏ việc lặp lại. Đừng tự động dùng AI để loại bỏ sự hiểu biết.
Trong thực tế, điều đó khiến cách tôi làm việc giống một bài toán phân bổ cơ hội học hỏi hơn là chỉ phân bổ nhiệm vụ.
1. Tự mình nắm những điều không được phép sai
Trước khi AI triển khai, tôi phải biết điều gì không được phép sai:
- Ranh giới tin cậy.
- Giới hạn độ trễ.
- Nguồn dữ liệu nào là nguồn sự thật.
- Hệ thống phải hành xử thế nào khi có lỗi.
- Các ràng buộc về quyền riêng tư.
Nếu tôi chưa biết những điều đó, đây chưa phải là lúc giao việc triển khai cho AI.
2. Dự đoán trước khi hỏi
Với những phần có giá trị học tập cao, tôi cố buộc mình dự đoán hành vi hoặc nút thắt trước khi hỏi AI.
Có một cơ sở thực nghiệm cho cách làm này, nhưng cần nói đúng phạm vi. Kornell, Hays và Bjork (2009) thấy rằng thử trả lời rồi được xem đáp án, kể cả khi trả lời sai, giúp người tham gia học tốt hơn so với chỉ đọc câu hỏi cùng đáp án. Họ dùng câu hỏi kiến thức và liên tưởng từ, không dùng profiler hay tác tử lập trình. Việc dự đoán nút thắt trước khi hỏi AI là cách tôi vận dụng ý tưởng ấy, không phải một hiệu quả đã được đo trực tiếp trong công việc này.
3. Giao phần triển khai, đừng giao luôn sự tò mò
Code lặp lại, migration, test cơ học hay những lần sửa cấu trúc đơn giản có thể giao cho AI.
Nhưng khi profiler, lỗi hay benchmark cho ra một điều bất ngờ, tôi muốn tự nhìn vào nó trước khi hỏi AI giải thích.
4. Giữ bằng chứng của con đường, không chỉ lấy đáp án cuối
Với một thay đổi không đơn giản, tôi muốn giữ lại các phương án đã thử, giả định quyết định thiết kế, log lỗi và kết quả benchmark. Một lời giải thích nghe hợp lý sau khi xong việc chưa đủ; nó cần đối chiếu được với những thử nghiệm thực sự đã chạy.
Với tôi, diff cuối cùng chưa đủ để đánh giá những giả định và phương án đã bị loại. Điều tôi muốn giữ là bằng chứng có thể kiểm tra, phù hợp với khuyến nghị của Anthropic về phản hồi từ môi trường và tính minh bạch của tác tử.
5. Chứng minh rằng mình thực sự sở hữu nó
Một thực hành tôi đề xuất là đóng diff sau khi đọc một thay đổi quan trọng, rồi tự giải thích lại. Nghiên cứu self-explanation của Chi và cộng sự (1989) quan sát thấy người học hiểu tốt hơn tạo nhiều lời giải thích nối các bước giải với nguyên lý. Nghiên cứu dùng bài tập cơ học; checklist dưới đây là ứng dụng tôi đề xuất cho code review, không phải quy trình đã được nghiên cứu đó kiểm chứng.
Thử giải thích từ trí nhớ:
- Dữ liệu đi đâu?
- Trạng thái nằm ở đâu?
- Lỗi có thể xảy ra như thế nào?
- Tại sao kiến trúc lại như vậy?
- Yêu cầu nào trong tương lai sẽ khiến thiết kế hiện tại không còn đúng?
Đây cũng là một thói quen tôi đang dần đưa vào cách làm việc với tác tử AI: sau khi AI tạo ra thứ gì đó, câu hỏi cuối cùng không chỉ là:
“Nó có chạy không?”
mà còn là:
“Tôi có thể tự giải thích tại sao nó chạy không?”
Nếu không làm được, tôi đã đưa code vào hệ thống nhưng chưa thực sự sở hữu nó.
Mục tiêu không phải kéo năng suất xuống để “học cho khổ”.
Mục tiêu là giữ lại những vòng phản hồi tạo nên khả năng phán đoán.
Có lẽ “biết code” vẫn quan trọng — nhưng vì một lý do khác
Có một câu hỏi đáng đặt ra:
Nếu AI code được thì còn cần học code không?
Tôi nghĩ câu hỏi này hơi sai.
Nếu “biết code” chỉ nghĩa là nhớ cú pháp, tự tay gõ CRUD thật nhanh hay thuộc API của framework, tôi không muốn lấy riêng những điều ấy làm thước đo năng lực trong cách làm việc với AI.
Nhưng code còn là một giao diện để suy nghĩ về hệ thống.
Đọc luồng thực thi. Đặt breakpoint. Thay đổi một giả định. Chạy benchmark. Viết một thử nghiệm nhỏ. Phá một lớp trừu tượng để xem bên dưới thực sự xảy ra gì.
Những hành động ấy là cách kỹ sư chất vấn thực tế.
Theo nghĩa đó, viết code giống làm thí nghiệm hơn là đánh máy.
Tôi hình dung một phép so sánh: nhà vật lý có thể dùng thiết bị do người khác chế tạo, nhưng vẫn cần đặt câu hỏi và kiểm tra cách diễn giải số đo. Nếu một thí nghiệm giả định chỉ còn là gửi lệnh cho AI rồi nhận biểu đồ cuối cùng, tôi sẽ muốn biết người thực hiện đã hiểu hiện tượng đến đâu.
Phần mềm cũng vậy.
Ta không cần tự viết tất cả code.
Nhưng ta cần duy trì khả năng đi đủ sâu vào hệ thống để tự xây dựng một lý thuyết độc lập về cách nó hoạt động.
Đó có thể là ý nghĩa mới của “biết code”.
Lập trình viên thời AI không chỉ là người điều phối
Trong Lập trình không còn vui nữa?, tôi từng hình dung sự dịch chuyển từ một người trực tiếp triển khai sang một người điều phối, thiết kế và đánh giá.
Tôi vẫn nghĩ hướng dịch chuyển ấy đang xảy ra.
Nhưng bây giờ tôi nghĩ cách nhìn đó chưa đủ.
Nó khiến lập trình viên tương lai nghe giống một người quản lý đội ngũ tác tử AI:
chia việc, đọc báo cáo, phê duyệt kết quả.
Với tôi, hình mẫu kỹ sư giỏi cần nhiều hơn khả năng điều phối việc tạo ra sản phẩm.
Họ xây dựng lý thuyết. Họ nhận ra mâu thuẫn. Họ nhìn một thất bại và thấy cả một nhóm vấn đề phía sau. Họ biến một cách chữa cháy thành một lớp trừu tượng. Họ phát hiện yêu cầu ban đầu đang đặt sai câu hỏi. Họ bước vào quá trình triển khai với một vấn đề và bước ra với một vấn đề tốt hơn.
Đó không phải chỉ là quản lý.
Đó là khám phá.
Và có lẽ đây chính là nơi “chất riêng” của lập trình viên sẽ tồn tại khi code trở nên dư thừa.
Không phải ở số dòng code bạn tự viết.
Không phải ở việc bạn từ chối AI.
Cũng không phải chỉ ở việc bạn ra lệnh cho AI tốt hơn người khác.
Mà ở:
những lý thuyết bạn xây dựng trong đầu,
những câu hỏi bạn phát hiện trên đường đi,
những thí nghiệm bạn nghĩ ra,
những thất bại bạn biết cách đọc,
và tri thức bạn có thể rút ra khỏi một hệ thống sau khi xây dựng nó.
Hai lập trình viên có thể sử dụng cùng một mô hình AI. Cùng IDE. Cùng một hệ thống tác tử. Cùng một lượng tài nguyên tính toán.
Một người hoàn thành được tính năng.
Người kia hoàn thành tính năng và bước ra khỏi dự án với một cách hiểu mới về cả một nhóm vấn đề.
Đó là nơi khác biệt bắt đầu xuất hiện.
Nhưng chính code từng tạo nên chúng ta
AI đang làm một điều tuyệt vời.
Trong trải nghiệm AnyLearning tôi đã kể, nó giúp tôi hoàn thành phần triển khai vốn bị trì hoãn. Đó là lợi ích tôi muốn tiếp tục khai thác.
Tôi muốn nhiều hơn, không phải ít hơn.
Tôi muốn AI tự viết migration. Tôi muốn nó sửa những lỗi lặp lại. Tôi muốn nó thử mười cấu hình khác nhau. Tôi muốn chi phí biến một ý tưởng thành phần mềm chạy được tiếp tục tiến gần về không.
Nếu chi phí triển khai tiếp tục giảm, tôi nghĩ chúng ta cần đánh giá riêng một kết quả vốn dễ bị gộp chung với việc hoàn thành dự án:
quá trình hình thành người kỹ sư.
Đó là ý tôi rút ra từ cách Naur nhìn việc lập trình: sản phẩm chạy được và hiểu biết của người làm là hai phần cùng đáng quan tâm.
Chúng ta tưởng mình đang xây phần mềm.
Nhưng trong lúc gỡ lỗi, sửa cấu trúc, chạy benchmark, thất bại và thử lại, phần mềm cũng đang xây lại cách chúng ta suy nghĩ.
Các nghiên cứu về AI và hiểu biết tức thời khiến tôi nghĩ chúng ta càng cần chủ động nối hai quá trình ấy với nhau.
Và vì thế câu hỏi quan trọng không còn chỉ là:
AI có thể viết bao nhiêu code thay chúng ta?
Mà là:
Những phần nào của việc viết code trước đây đã âm thầm tạo nên chính chúng ta — và làm thế nào để giữ lại chúng khi máy không còn cần chúng ta trực tiếp làm phần việc đó?
Nếu trả lời được câu hỏi này, AI không nhất thiết khiến thế hệ lập trình viên tiếp theo yếu hơn.
Ngược lại, nó có thể tạo ra một thế hệ kỹ sư được giải phóng khỏi việc lặp lại nhưng vẫn giữ được sự tò mò, chiều sâu và khả năng phán đoán.
Những người không cần tự đi bộ trên mọi con đường.
Nhưng biết khi nào phải bước xuống khỏi chiếc trực thăng để thực sự nhìn thấy địa hình.
Đó là kiểu lập trình viên tôi muốn trở thành trong thời đại AI.
Và quan trọng hơn, đó là kiểu lập trình viên tôi nghĩ chúng ta cần biết cách tạo ra.
Các bài viết liên quan
Bài này nằm ở giao điểm của một chuỗi câu hỏi tôi đã viết trong năm nay:
Lập trình không còn vui nữa? Nếu AI làm phần lớn việc triển khai, lập trình viên còn tìm thấy niềm vui và giá trị nghề nghiệp ở đâu?
AI Is Making Us Faster Learners and Worse Thinkers at the Same Time AI có thể cải thiện kết quả công việc đồng thời làm suy yếu quá trình xây dựng sự hiểu biết như thế nào?
The Bottleneck Moved to Review Khi việc viết code ngày càng rẻ, nút thắt dịch chuyển sang kiểm chứng và khả năng phán đoán của con người như thế nào?
Ask, or It Will Guess Khi tác tử AI có thể tự quyết định phần lớn cách triển khai, làm thế nào để con người vẫn sở hữu vấn đề, giả định và quá trình suy luận?
The GPU Was Already There Một ví dụ thực tế về lý do đo đạc, thất bại và va vào hệ thống thật vẫn tạo ra những hiểu biết mà tự động hóa phần triển khai không thể tự mang lại.
Nguồn tham khảo
-
Terence Tao: Navier–Stokes và giá trị của quá trình tìm lời giải, 3/9/2026; tạo, kiểm chứng và tiêu hóa chứng minh, 22/4/2026.
-
Peter Naur: Programming as Theory Building, 1985.
-
Anthropic: How AI Assistance Impacts the Formation of Coding Skills, 29/1/2026.
-
Alberto Martin-Lopez và cộng sự: More Code, Less Understanding? On the Impact of AI Assistants on Developers’ Productivity and Code Ownership, 2026.
-
Margaret-Anne Storey: From Technical Debt to Cognitive and Intent Debt: Rethinking Software Health in the Age of AI, 2026.
-
Nate Kornell, Matthew Jensen Hays và Robert A. Bjork: Unsuccessful Retrieval Attempts Enhance Subsequent Learning, 2009.
-
Michelene T. H. Chi và cộng sự: Self-Explanations: How Students Study and Use Examples in Learning to Solve Problems, 1989.
-
Su và Cardie: Knowing but Not Showing: LLMs Recognize Ambiguity but Rarely Ask Clarifying Questions, 2026.
-
Anthropic: Building Effective Agents.
-
NVIDIA: Triton dynamic batching; PyTorch: Automatic Mixed Precision examples.
-
LLVM: Register allocation; PostgreSQL: B-tree indexes, write-ahead logging.
-
GitHub: GitHub Actions, code scanning.
