Tại sao lại có một người mới của người Viking trong Go?


49

Tôi vẫn còn bối rối như tại sao chúng ta có newtrong Go.

Khi bạn muốn khởi tạo một cấu trúc, bạn làm

t := Thing{}

và bạn có thể lấy một con trỏ đến một thể hiện mới bằng cách thực hiện

t := &Thing{}

Nhưng cũng có khả năng này:

t := new(Thing)

Điều cuối cùng này có vẻ hơi xa lạ với phần còn lại của ngôn ngữ. &Thing{}rõ ràng và súc tích như new(Thing)và nó chỉ sử dụng các cấu trúc bạn thường sử dụng ở nơi khác. Nó cũng mở rộng hơn khi bạn có thể thay đổi nó thành &Thing{3}hoặc &Thing{Feets:7}.

Theo tôi, việc có một từ khóa bổ sung 1 rất tốn kém, nó làm cho ngôn ngữ trở nên phức tạp hơn và thêm vào những gì bạn phải biết. Và nó có thể che dấu cho những người mới đến những gì đằng sau việc tạo ra một cấu trúc.

Nó cũng làm cho một từ dành riêng nhiều hơn.

Vậy lý do đằng sau là newgì? Nó đôi khi hữu ích? Chúng ta có nên sử dụng nó?


1 : Vâng, tôi biết đó không phải là một từ khóa ở cấp độ ngữ pháp, bạn có thể theo dõi nó , nhưng điều đó không thay đổi thực tế, đối với nhà phát triển hợp lý, một từ dành riêng.


3
"... tới các lập trình viên ..." - đây là lý do. F # / Haskell / v.v. rất xa lạ với các nhà phát triển C và đó là lý do tại sao họ có lực kéo ~ 0. Scala đã nỗ lực và bây giờ nó dễ tiếp cận và nghe nói hơn.
Den

12
Cùng một quan niệm, Python và Ruby rất xa lạ với các nhà phát triển C, vì họ sử dụng một loạt các từ khóa lạ, quy tắc cú pháp "kỳ lạ" (niềng răng ở đâu?) Và các khái niệm ngữ nghĩa kỳ lạ (máy phát điện? Siêu trang trí? Trang trí?). Tuy nhiên, họ không nhận được ~ 0 lực kéo, hoàn toàn ngược lại.
Xion

8
@Xion: bạn đã xem tốc độ tăng trưởng ban đầu của Ruby chưa? Phải mất nhiều thời gian để có được vị trí như bây giờ (chính xác là 18 năm). Python thậm chí còn cũ hơn (1991!).
Joachim Sauer

2
@AresresF. Một số kháng cự đối với Scala có thể không liên quan gì đến ngôn ngữ. Là một lập trình viên trẻ hơn (25 tuổi), một cái gì đó về chính cái tên khiến tôi nghĩ về sự giao thoa giữa một ngôn ngữ dựa trên toán học như Matlab (mà tôi có những ký ức tồi tệ) và một thứ thực sự cũ như Fortran. Chưa bao giờ có bất kỳ sự thôi thúc nào để nhìn vào nó.
Izkata

4
Một lưu ý phụ: mới không phải là một từ khóa trong Go. Đây là một chức năng tích hợp.
Manish Malik

Câu trả lời:


44

Cách tốt nhất để hỏi có lẽ là với những người làm việc trên nó; chính xác những gì tôi đã làm !

Tl; dr: nó đã được ban có trước make&{}, và nó vẫn còn chức năng để sử dụng trong một số trường hợp.

Về cơ bản, đây là những phần quan trọng nhất được trích dẫn:

Vậy lý do đằng sau mới là gì? Nó có phải là một cái gì đó hữu ích? Chúng ta có nên sử dụng nó?

Bạn không thể làm điều này mà không có mới

v := new(int)
*v++
fmt.Println(*v)

mới không phải là một tính năng tiêu đề của Go, bạn sẽ không thấy nó được sử dụng thường xuyên, nhưng khi bạn cần nó, nó sẽ ở đó.

Chúc mừng

Dave

Sau một câu trả lời khác cho thấy loại giải pháp này:

vv := 0
v := &vv
*v++
fmt.Println(*v)

Tôi yêu cầu làm rõ thêm:

Vì vậy, về cơ bản, quan điểm của Dave không thực sự đứng vững?

Có những nơi thật bất tiện khi lẻn vào một biến mới chỉ để lấy địa chỉ của nó.

new (T) có nghĩa đơn giản ngay lập tức, thay vì là một thành ngữ gồm nhiều bước.

Quan điểm của Dave chỉ giảm nếu khả năng kỹ thuật đơn thuần (thực hiện mà không có new) là hấp dẫn.

Không phải điều này đã được thảo luận bởi vì rõ ràng là Go nên có nó bởi vì hầu hết mọi ngôn ngữ đều có nó?

"Chúng ta sẽ giữ new?" thảo luận bật lên theo thời gian. Vì chúng ta không thể lấy nó ra cho đến khi đi 2, nếu tôi hiểu đúng về Lời hứa, dường như không có gì nhiều để đi vòng vòng một lần nữa; vào thời điểm Go 2 có thể nghĩ được, chúng ta có thể có một số ý tưởng khác biệt và tốt hơn ...

Chris

Nó cũng chủ yếu là vì lý do lịch sử:

bạn cần xem xét lịch sử của dự án. Tôi nghĩ rằng mới được giới thiệu đầu tiên trước khi có.

Điều đó đúng. Trong thực tế, chúng tôi đã đấu tranh một thời gian trước khi đưa ra ý tưởng thực hiện. Nếu bạn nhìn vào nhật ký kho lưu trữ, bạn có thể thấy nó chỉ hiển thị vào tháng 1 năm 2009, bản sửa đổi 9a924177598f.

Hàm dựng sẵn mới cũng đi trước ý tưởng về & {} để lấy địa chỉ của một chữ hỗn hợp (và cú pháp đó theo một nghĩa nào đó là sai; có lẽ phải là (* T) {các trường của T} nhưng không đủ lý do để thay đổi nó).

Hàm mới không thực sự cần thiết nhưng mã dường như sử dụng nó trong thực tế. Tại thời điểm này thật khó để thoát khỏi nó.

Ian


Tôi sẽ rất vui khi thấy các liên kết đến cái khác "chúng ta sẽ giữ mới chứ?" thảo luậnbật lên bất cứ lúc nào .
Denys Séguret

Có điều gì ngăn cản bạn làm v := &(0)và bỏ qua biến tạm thời? (Tôi biết không đi.)
Alex Feinman

3
@AlexFeinman Là 0một hằng số theo nghĩa đen, bạn không thể lấy địa chỉ của nó. Một vấn đề sẽ xảy ra nếu bạn cũng muốn một loại cụ thể. Đó là lý do tại sao một cú pháp như &inthoặc &int(0)có thể hữu ích (mặc dù không nghĩ nhiều về cú pháp tốt nhất). Nhưng thực hiện nó trong hai dòng như Collins cho thấy cũng tốt ( vv := 0; v := &vv).
Denys Séguret

14
"Vì chúng tôi không thể lấy nó ra cho đến khi đi 2" ... mà, như mọi người đều biết, sẽ không bao giờ xảy ra vì Go 2được coi là có hại.
Mason Wheeler

2
@MasonWheeler bạn gần như đã giết tôi ... vẫn cười vào "Đi 2 được coi là có hại" ... thật kỳ lạ là tôi đã nói về bài báo đó hôm nay vào bữa trưa.
Daniela Petruzalek
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.