#Why can I have non-public struct functions, but can't have non-public fields?

1 messages · Page 1 of 1 (latest)

tall tinsel
#

To explain why they are different: Fields affect the size and representation of the struct, whereas functions do not (the functions take space elsewhere, and are merely namespaced in a struct).

As for the ability to declare fields as private, you can see an old closed proposal with discussion here: https://github.com/ziglang/zig/issues/9909

#

Long story short, when you return a struct to a caller, you are giving that caller a chunk of data, and it was decided that it doesn't make sense to hide parts of that data from them. If you do need to hide info, you can always use an opaque pointer a la many C APIs.

#

Although that's less idiomatic Zig and does result in type erasure, taking away some safety benefits.

dry mango
#

private fields are more of an obfuscation mechanism

#

so if all you need is to obfuscate data, e.g. make it harder to access and use, you can still do that

#

one strategy is to make a field like private: struct {...}, which contains all the data you want to handle as internal

#

or another even more obfuscated way of doing it is to have it in the struct as an opaque bag of bytes/bits

#

e.g.

pub const Foo = struct {
    public: u32,
    private: [@sizeOf(PrivateData)]enum(u8) { _ } align(@alignOf(PrivateData)),

    // these decls aren't available to any other files, and thus invisible to external consumers of this type.
    // that means the representation of the `private` field is opaque.
    const PrivateData = struct {
        bar: u32,
        baz: f32,
    };
    fn privateDataPtr(foo: *Foo) *PrivateData {
        return std.mem.bytesAsValue(PrivateData, &foo.private);
    }
};

that's effectively what private fields boil down to: regions of data whose representation and meaning are opaque to the user of the type

tall tinsel
#

Definitely, there are several ways to obfuscate/hide some of the the data, those are some good additions.

I don't think I did a good job explaining the motivation for the design choice — as always, Andrew's reasoning is spelled out pretty well in the issue I linked