Earlier quoted context omitted.
It’s how structs work in C though, and Go is spiritually very close to C, including explicit pointer types, address-taking and dereferencing.
Not necessarily. A string in C is usually a char . If you have a struct with a char and you copy it, you copy the pointer to the backing memory. This is analogous to Go which also has a String be a pointer to the heap, but the behavior is different. Go’s String is a char* that behaves like a char[] when copied.
Go structs are copied on assignment (and other things about Go I'd missed)
71–80 of 176 posts
Re: Go structs are copied on assignment (and other things about Go I'd missed)
#72The semantics of when stuff is copied, moved, or passed by reference are all over the place in language design. C started with the idea that functions returned one int-sized value in a register. This led to classic bugs where the function returns a pointer to a local value. Compilers now usually catch this. C eventually got structure return by copy. Then C++ added return value by move, and automatic optimization for…
That's one little reason why Rust is loved by many: immutability by default. Meanwhile, it's not even possible in Go to declare immutable variables!
Re: Go structs are copied on assignment (and other things about Go I'd missed)
#73To generalize the title into a rule is good to remember that in Go everything is passed by value(copy).
That is the case for almost every modern language. C++ is one of the few languages that has "references" and at least last I looked that's a language accommodation over what are pointers being passed by value in the assembly, at least until compiler optimizations take over (and that's not limited to references either). If you're in 2024 and you're in some programming class making a big deal about pass-by-value versus…
foo: proc options(main);
dcl sysprint print;
dcl a(3) fixed bin(31) init(1,2,3);
put skip data (a);
call bar(a);
put skip data (a);
bar: proc(x);
dcl x(3) fixed bin(31);
dcl b(3) fixed bin(31) init(3,2,1);
x = b;
b(1) = 42;
x(2) = 42;
put skip data (b);
put skip data (x);
end bar;
end foo;
outputs A(1)= 1 A(2)= 2 A(3)= 3 ;
B(1)= 42 B(2)= 2 B(3)= 1 ;
X(1)= 3 X(2)= 42 X(3)= 1 ;
A(1)= 3 A(2)= 42 A(3)= 1 ;
demonstrating that X refers to A in BAR and assigning B to X copies B into X (= A).Re: Go structs are copied on assignment (and other things about Go I'd missed)
#74The semantics of when stuff is copied, moved, or passed by reference are all over the place in language design. C started with the idea that functions returned one int-sized value in a register. This led to classic bugs where the function returns a pointer to a local value. Compilers now usually catch this. C eventually got structure return by copy. Then C++ added return value by move, and automatic optimization for…
Re: Go structs are copied on assignment (and other things about Go I'd missed)
#75Re: Go structs are copied on assignment (and other things about Go I'd missed)
#76The semantics of when stuff is copied, moved, or passed by reference are all over the place in language design. C started with the idea that functions returned one int-sized value in a register. This led to classic bugs where the function returns a pointer to a local value. Compilers now usually catch this. C eventually got structure return by copy. Then C++ added return value by move, and automatic optimization for…
> There's a good argument for immutability by default, but many programmers dislike all the extra declarations required. That's one little reason why Rust is loved by many: immutability by default. Meanwhile, it's not even possible in Go to declare immutable variables!
Re: Go structs are copied on assignment (and other things about Go I'd missed)
#77Looks as though the range loop isn't an issue from Go 1.22 anymore. https://go.dev/blog/loopvar-preview
The question there is, does our for-each style loop make a new variable each iteration, with the appropriate value, or does it have a single variable and it's just re-assigned for each iteration. People who haven't designed a language before might think the second option sounds optimal and won't make a practical difference, but it's actually very annoying and that's why Go changed to the former.
This time though it's not about the variable staying the same, the problem is that we got a copy of the data we cared about, not a mutable reference to that data.
Re: Go structs are copied on assignment (and other things about Go I'd missed)
#78The semantics of when stuff is copied, moved, or passed by reference are all over the place in language design. C started with the idea that functions returned one int-sized value in a register. This led to classic bugs where the function returns a pointer to a local value. Compilers now usually catch this. C eventually got structure return by copy. Then C++ added return value by move, and automatic optimization for…
> There's a good argument for immutability by default, but many programmers dislike all the extra declarations required. That's one little reason why Rust is loved by many: immutability by default. Meanwhile, it's not even possible in Go to declare immutable variables!
The real problem is just visibility: am I editing a copy of the original? Who else can edit the original? Who's going to?
I'd argue those two questions are what we actually want to know the answer to, and immutability criteria are just an awkward compromise solution.
Re: Go structs are copied on assignment (and other things about Go I'd missed)
#79This sometimes catches out people C#/.Net too, it's a big difference between Class and Struct, Class is reference type and Struct is value type. (see fiddle below), but in practice people very rarely reach for structs, so people don't tend to build up the muscle memory of using them, even if they intuitively understand the difference between reference types and value types from general use of other types. (Fiddle dem…
Non-C# developer question: what use-case/situation would a `struct` make sense to use instead of a `class`? Just out of curiosity. [Edit] Well, there's a nice, special article for this very question: https://learn.microsoft.com/en-us/dotnet/standard/design-gui...
Imagine you have a Dictionary. (That is, a dictionary (hash lookup) from type TKey to type TValue ).
Imagine your choice of key is a composite of 4 bytes, and you want to preserve the meaning of each, so let's say you define a class (shorthand to avoid all the get/set cruft):
class MyKey {
byte A;
byte B;
byte C;
byte D;
}
When you profile your memory usage, to your horror you discover you actually have a keysize of 64 bits for the reference to the location on the heap.If however you use a struct, then your key is actually the 4 bytes that defines your key.
In modern .Net, you'd probably be better off defaulting to use a record (correction: record struct) type for this purpose unless you have very specific reasons for wanting fine-grained control over memory layout with the StructLayout Attribute.
See this article for using StructLayout:
https://learn.microsoft.com/en-us/dotnet/api/system.runtime....
Re: Go structs are copied on assignment (and other things about Go I'd missed)
#80One of the many things I find inspiring about Julia is how quick she is to admit to mistakes she has made or things that she hasn't understood. If she didn't understand it, I can 100% guarantee that there are large numbers of people out there who also didn't understand it - many of whom were probably too embarrassed to ever admit it. I think this is a useful trait for senior software engineers generally. If you're a…
Personally, I think that the idea that programmers should know everything is kinda bizarre. Programming is about finding the answer. If you already knew everything, you could just sit down and type any program from your knowledge. We all know that you can't know everything otherwise, why even write documentation or use git? Unfortunately, it's difficult to move past this idea, and it's so pervasive that stating "I do…
It is also insanely difficult for a doctor/surgeon to admit a mistake without being punished severly.