CFSDN nhấn mạnh vào giá trị tạo ra nguồn mở và chúng tôi cam kết xây dựng nền tảng chia sẻ tài nguyên để mọi nhân viên CNTT có thể tìm thấy thế giới tuyệt vời của bạn tại đây.
Bài viết trên blog CFSDN này về những cạm bẫy thường gặp trong ngôn ngữ Go được tác giả sưu tầm và biên soạn. Nếu các bạn quan tâm tới bài viết này thì nhớ like nhé.
giới thiệu
Loạt bài này sẽ liệt kê một số câu hỏi phổ biến trong các cuộc phỏng vấn cờ vây.
Vấn đề vòng lặp cắt
Vòng lặp For có thể được sử dụng rất nhiều trong quá trình viết mã hàng ngày của chúng ta. Trong nhiều tình huống kinh doanh, chúng ta cần sử dụng để xử lý vòng lặp. Tuy nhiên, có một số vấn đề cần chú ý khi sử dụng vòng lặp for trong golang. Bạn có gặp phải vấn đề gì không? Đầu tiên hãy nhìn vào đoạn mã sau:
- hàm kiểm tra lát cắt()
- a:=[]int64{1,2,3}
- vì_,v:=rangea{
- gofunc(){
- fmt.Println(v)
- }()
- }
-
- thời gian.Ngủ(thời gian.Thứ hai)
- }
-
- đầu ra:333
Vậy tại sao lại có kết quả này?
Trong vòng lặp for của golang, các biến hàm được tạo bên trong vòng lặp đều có chung địa chỉ bộ nhớ và vòng lặp for luôn sử dụng cùng một bộ nhớ để nhận giá trị của biến giá trị trong vòng lặp. Cho dù nó có được lặp bao nhiêu lần thì địa chỉ bộ nhớ của giá trị vẫn như nhau. Chúng ta có thể kiểm tra nó:
- functestSliceWithAddress(){
- a:=[]int64{1,2,3}
- vì_,v:=rangea{
- gofunc(){
- fmt.Println(&v)
- }()
-
- }
-
- thời gian.Ngủ(thời gian.Thứ hai)
- }
-
- đầu ra:
- 0xc0000b2008
- 0xc0000b2008
- 0xc0000b2008
Như mong đợi. Nếu quan tâm hơn, bạn có thể in ra tập hợp mã này và bạn sẽ thấy rằng vòng lặp v đang vận hành cùng một bộ nhớ.
Tương tự, chúng ta sẽ gặp một vị trí thú vị khác trong vòng lặp slice. Bạn có thể xem đầu ra của đoạn mã sau là gì?
- functestRange3(){
- a:=[]int64{1,2,3}
- vì_,v:=rangea{
- a=thêm(a,v)
- }
-
- fmt.Println(a)
- }
Đầu ra của mã này là: [1 2 3 1 2 3], tại sao? Bởi vì golang sẽ sao chép a trước khi lặp và sau đó hoạt động trên a mới được sao chép, do đó số vòng lặp sẽ không thay đổi khi tăng thêm.
So sánh giữa giao diện và con số không
Ví dụ: một con trỏ rỗng được trả về nhưng nó không phải là giao diện rỗng.
- Giao diện functest(){
- phải:=func(argsố nguyên)giao diện{}{
- varresult*struct{}=nil
- nếu tham số>0{
- kết quả=&struct{}{}
- }
-
- trở lạikết quả
- }
-
- ifres:=must(-1);res!=nil{
- fmt.Println("kết quả:",độ phân giải)
- }
- }
Kết quả đầu ra là: result: , tại sao? Vì các biến trong go có hai thuộc tính: kiểu và giá trị. Khi so sánh, chúng sẽ chỉ được coi là bằng nhau khi kiểu và giá trị giống nhau. Kiểu kết quả trong code là con trỏ và giá trị là 0 nên sẽ có kết quả như thế này.
Tham số biến là loại giao diện trống
Khi tham số biến của tham số là loại giao diện trống, bạn cần chú ý đến vấn đề mở rộng tham số khi truyền vào lát cắt của giao diện trống.
- functestVolatile(){
- be=[]giao diện{}{1,2,3}
-
- fmt.Println(a)
- fmt.Println(a...)
- }
Đầu ra là:
- [123]
- 123
Thứ tự khi duyệt bản đồ không cố định.
Đừng tin vào thứ tự của bản đồ.
- Bản đồ chức năng()
- m:=bản đồ[chuỗi]chuỗi{
- "Một":"Một",
- "b":"b",
- "c":"c",
- }
-
- vìk,v:=phạm vi{
- println(k,v)
- }
- }
Vì lý do cụ thể, bạn có thể xem mã nguồn: map.go:mapiterinit và bạn sẽ thấy rằng mã bên dưới được sử dụng để xác định nơi bắt đầu duyệt qua bản đồ. Một lý do khác là việc di chuyển và sắp xếp lại các phím sẽ diễn ra trên bản đồ trong một số trường hợp cụ thể nhất định (chẳng hạn như mở rộng). Quá trình truyền tải là duyệt qua nhóm theo thứ tự, đồng thời duyệt qua các khóa trong nhóm theo thứ tự. Sau khi di dời, vị trí của chìa khóa đã thay đổi đáng kể nên kết quả duyệt bản đồ không thể theo đúng thứ tự ban đầu.
- funcmapiterinit(t*maptype,h*hmap,it*hiter){
- ......
- //quyết địnhỞ đâuĐẾNbắt đầu
- r:=uintptr(fastrand())
- ......
- }
Liên kết gốc: https://mp.weixin.qq.com/s/tcBH86xcN_VXIq4mzaVRkQ.
Cuối cùng, bài viết về những cạm bẫy phổ biến trong ngôn ngữ Go kết thúc tại đây. Nếu bạn muốn biết thêm về những cạm bẫy phổ biến trong ngôn ngữ Go, vui lòng tìm kiếm các bài viết của CFSDN hoặc tiếp tục duyệt các bài viết liên quan. Tôi hy vọng bạn sẽ ủng hộ tôi trong tương lai! .
Tôi là một lập trình viên xuất sắc, rất giỏi!