ChanServ changed the topic of #zig to: zig programming language | https://ziglang.org | be excellent to each other | channel logs: https://irclog.whitequark.org/zig/
<leeward> So on to the second question: should it? It seems like "any" is at least as clear as "anytype" without the weird agglomerative naming, and without the confusion with "type"
<shakesoda> but they're different?
<shakesoda> isn't it constrained to types as the name suggests, for really actually anything there's var
<gruebite> i feel like there should be a way to explicitely state two types with the same layout are in fact the same
<gruebite> i see a lot of reimplementations of Color, Vectors, etc. each application with their own
<gruebite> if the layout is the same, why not make them convertable to each other to allow for your own extensions/functions
<shakesoda> duck typing would be useful for that although i don't fundamentally mind this much
<gruebite> when using a library and you intend to expose similar functionality (similar type) but instead of exposing implementation details from internal libraries used, would you rather expose your own type compatible with your dependency's?
<gruebite> i see this a lot in games, and i think it's kinda smelly. libA depends on libB, both have a Vec2 type or whatever
<shakesoda> there's usually just some interaction point where i can trivially convert to the one i want while doing something else
<shakesoda> for my own purposes (surprise: it's games) i usually want my own types to begin with, and don't rely much on deps
<gruebite> but most of the methods end up being duplicated or deferred?
<gruebite> erm
<gruebite> s/deferred/delegated
<shakesoda> it just isn't really a concern in practice if that happens to some extent as long as the code i'm dealing with is clear
<shakesoda> although, to be sure, i would of course prefer not duping functionality, and to that end i will intern deps and gut the types sometimes if that seems like it'll keep things simpler
<gruebite> depends on the type, i think
<ronsor> `anytype` is fine
<ronsor> it stands for any type
<ronsor> easy
<shakesoda> i do think there would be some value in a way to express duck types
<shakesoda> maybe there's a decent way to go about it already
<shakesoda> if you can cast such that it has to match memory layout
<gruebite> can't use native zig structs, i think
<ronsor> extern struct/packed struct only
<ronsor> otherwise the fields can be reordered
Ristovski has quit [Quit: 0]
[Ristovski] has joined #zig
rzezeski has quit [Quit: Connection closed for inactivity]
rzezeski has joined #zig
craigo has quit [Ping timeout: 260 seconds]
<daurnimator> ifreund: on linux, compare the inode against /proc/self/root
<ronsor> I have discovered another bug
xackus has joined #zig
xackus_ has quit [Ping timeout: 240 seconds]
waleee-cl has quit [Quit: Connection closed for inactivity]
r4pr0n has quit [Remote host closed the connection]
craigo has joined #zig
knebulae has quit [Read error: Connection reset by peer]
simontime has quit [Quit: ZNC 1.8.0 - https://znc.in]
mgxm has quit [Quit: ....]
mgxm has joined #zig
<daurnimator> > The GNU C Library version 2.32 is now available.
decentpenguin has quit [Quit: ZNC crashed or something]
decentpenguin has joined #zig
ur5us has quit [Ping timeout: 260 seconds]
frett27 has joined #zig
frett27 has quit [Ping timeout: 246 seconds]
frett27 has joined #zig
dermetfan has joined #zig
frett27 has quit [Ping timeout: 240 seconds]
ur5us has joined #zig
waleee-cl has joined #zig
ur5us has quit [Ping timeout: 264 seconds]
ur5us has joined #zig
<ifreund> andrewrk: don't worry about giving more feedback on #5985 for the moment, I think the initial steps are clear to me and it's time to try some implementation
ifreund has quit [Read error: Connection reset by peer]
ifreund has joined #zig
dddddd has quit [Ping timeout: 256 seconds]
heitzman1 has joined #zig
heitzmann has quit [Read error: Connection reset by peer]
dddddd has joined #zig
cren has joined #zig
[Ristovski] is now known as Ristovski
ur5us has quit [Ping timeout: 244 seconds]
nycex has quit [Remote host closed the connection]
nycex has joined #zig
knebulae has joined #zig
knebulae has quit [Read error: Connection reset by peer]
knebulae has joined #zig
waleee-cl has quit [Quit: Connection closed for inactivity]
euandreh has quit [Ping timeout: 272 seconds]
cren has quit [Ping timeout: 260 seconds]
heitzman1 has quit [Quit: WeeChat 2.9]
heitzmann has joined #zig
<alehander92> hey
<alehander92> are zig generics inspired by ML
* DarkUranium waves at alehander92
<alehander92> i was discussing ML modules and
<alehander92> .. yeah :D :D
<alehander92> it just seems to me there might be some little inspiration
<DarkUranium> Don't ask me, I am only here so I don't get fined!
<alexnask[m]> alehander92: I dont think so
<ifreund> Not to my knowledge, Zig generics just follow naturally from comptime and types as first class values at comptime
<ifreund> there isn't really anything in the zig spec that is generic-specific
<alehander92> i .. hope i don't get fined as well
<ifreund> they're just a thing you can do with comptime
<alehander92> ah, i see
<ifreund> that said, I'm not very familiar with ocaml
<alehander92> yeah i am talking about the design approach of letting this happen
<ifreund> (or any other ML)
<alexnask[m]> Right, I get what you mean alehander92 and I can see the parallels but I dont think Andrew is a functional programming fan
<alehander92> i see, it's quite possible indeed
<alexnask[m]> I think it was mainly a result of designing the language with comptime evaluation from the beginning
<fengb> There’s a talk where Andrew mentioned genetics just sorta fell out of implementing comptime
<alehander92> yes, makes sense
<alehander92> which reminds me then : is there a module concept
<ikskuh> alehander92: what is a "module"?
<alehander92> in zig : then comptime might lead to similar module functions
<alehander92> a collection of type and function signatures maybe
<ikskuh> we have that
<alehander92> a namespace
<ikskuh> it's called struct
<alexnask[m]> "modules" usually refer to files (at least in the compiler source) but at a language level imports just return structs
<alehander92> but as a value, not a file
<alehander92> hmm
<ikskuh> alehander92: i make you a example ;)
<fengb> Files are just structs
<ikskuh> yep
<alehander92> yeah cool
<fengb> Maybe we should rename them to modules 🤔
<alehander92> so in this case i can write a function that returns a new struct with changed types
<alehander92> e.g. importing generalized(x)
<alehander92> or something
<fengb> You alias it with const =
<fengb> const Stringer = std.ArrayList([]const u8)
<ikskuh> zlm is generic against a certain type
<ikskuh> by-default you can use zlm.Vec3 (which is specialized on f32)
<alehander92> yeah
<alehander92> exactly
<ikskuh> but you can also do zlm.specializeOn(i32).Vec3
<ikskuh> which is a Vec3 with int types
<fengb> Unlike MLs, Zig compiler actually has no idea what generics are. So stuff like dependent types don’t really exist
<fengb> But you can do self referencing function args to sorta fake it
<alehander92> i am mostly thinking of module functors
<alexnask[m]> Well it knows about generics in the sense of functions with comptime or anytype arguments but nothing special about type functions (generic functions that return types)
<alexnask[m]> -Wpedantic
<alexnask[m]> :P
<fengb> It’s more of a type theory thing. In proper genetics you can actually have args take Writer(T)
<fengb> Generics
<fengb> Zig doesn’t really follow proper theory a whole lot :P
<fengb> Brutally pragmatic in a good way
<alehander92> probably it's possible to adapt it more
<ikskuh> fengb: there's still the pending proposal of checked type parameters
<ikskuh> which i think are a good thing and better than the duck typing we have right now
<fengb> Yeah I’ve been watching that. Still not “real” generics but predicate checks can get us pretty close
<ikskuh> yeah, it improves error messages by a lot
<ikskuh> and also conveys information better what to expect for a type
<fengb> You don’t like `writer: anytype`??
<alexnask[m]> I agree with a lot of these points however I also like the flexibility of pure duck typing, some APIs may only use e.g. writeAll and you can pass a File directly (just an example)
euandreh has joined #zig
<ikskuh> alexnask[m]: yeah i think that will still be possible with this proposal
<alexnask[m]> In which case replacing the anytype with a Writer typechecker is limiting the actual functionality
<ikskuh> but you might plan your API for future extensions
<ikskuh> which needs a writeIntLittle at some point
<alexnask[m]> True, however naively one would use a Writer typechecker that would check for context + all Writer methods
<alexnask[m]> It definitely is useful in a lot of places
craigo has quit [Ping timeout: 240 seconds]
<alexnask[m]> s/is/would be
<alexnask[m]> I think some small library to define type checkers/concepts/w.e you want to call them would already really useful to get good compiler errors
* ikskuh is hacking some stuff in VBA atm
<ikskuh> we should never ever introduce "With" in zig
<ikskuh> alexnask[m]: yeah, true
<ikskuh> std.meta.traits.requiresFunction("foo");
<alexnask[m]> Like you could reasonably write something like this: https://zig.godbolt.org/z/5n5P7E
<alexnask[m]> (well, @TypeOf(writer) instead of writer)
<alexnask[m]> I may just do it later to train my comptime muscle
<fengb> comptime katas?
<ikskuh> alexnask[m]: that writer checker is already too strict :D
<ikskuh> => .{ .field, "context", ContextType },
<ikskuh> should not be required
<alexnask[m]> Sure, just an example
<alexnask[m]> :)
<companion_cube> ikskuh: what's `With`?
<companion_cube> (as for the predicates, it's like D, right?)
<leeward> We have defer, we don't need with.
<companion_cube> ah, so like python's with?
<leeward> Isn't there a ticket for something like that though? It keeps getting closed as too complicated then reopened as needed for async.
<fengb> Yeah resource tracking
<fengb> Biggest recent driver is cancelawait semantics
<leeward> Closures would solve this problem.
<leeward> Of course, they add extra allocation.
<companion_cube> imho generic containers are also a big point where RAII makes sense
<ifreund> but the complexity :(
<leeward> so much complexity
<companion_cube> the complexity has to be there somewhere, either in your code or in someone else's
<companion_cube> if you can `arraylist.truncate(42)` or whatever, you need to specify somewhere what happened to elements that die
<leeward> I think the bulk of the complexity comes from move/copy constructors.
<companion_cube> (of course you could have `arraylist.truncate(42, |x| x.deinit())` or something like that with closures)
<companion_cube> well the pb with C++ is that these are implicit
<ikskuh> companion_cube, fengb, leeward: it's a "import all of these things fields into the current namespace"
<companion_cube> (I guess I'm biased towards rust again)
<ikskuh> With foo
<ikskuh> .x = 10
<ikskuh> .y = 20
<companion_cube> ikskuh: oh ok
<ikskuh> End with
<ikskuh> .show()
<ikskuh> :D
<leeward> ikskuh: Oh, that's very different.
<alexnask[m]> I dont hate `With` tbh though Im happy I havent written VBA in a long time
<ikskuh> alexnask[m]: you're telling me you haven't ever seen people nesting With? :D
<alexnask[m]> Oh Ive seen it
<leeward> I'm a little confused. I've never written VBA and the last time I wrote VB it was 6. Is this like a usingnamespace block?
<ifreund> is it like with in python?
<ikskuh> yeah, but for object fields, not namespace members
<ikskuh> so if you have a point "p"
<ikskuh> you can do "With p \ .x = 10 \ .y = 20 \ End With"
<ikskuh> which would be equivalent to "p.x = 10 \ p.y = 20 \"
<leeward> What's the upside?
<alexnask[m]> Not quite, you can think of it as `With (some_expr)` making all `.foo` transform into `(some_expr).foo`
<alexnask[m]> (in the block)
<ikskuh> leeward, you have to type less :D
<ikskuh> you can also call methods on those :D
<leeward> I mean, I guess if you have really long names it might save you some columns, but...easier to write/harder to read doesn't sound very Ziggy.
<ifreund> wow that's terrible
<ifreund> python's with is totally different and rather useful
<leeward> entirely different
<fengb> JS has that too. It’s even worse because field accesses in with block look identical to variables
<leeward> context managers let you do what defer does, which is how we ended up in that raii discussion
<companion_cube> although in python you need a new indent at every `with`
<ronsor> VB-style 'with' would be a mistake
<leeward> companion_cube: ExitStack solves that "indent for every `with`" problem so you only need a single indent.
<SyrupThinker> > JS has that too In non-strict mode code only. So thats luckily mostly unused
<companion_cube> leeward: sounds like an ugly hack :)
<leeward> Maybe, but it works well.
<leeward> I had a work thing that needed to do a lot of acquire/release hardware, and it was very necessary. It also lets you do something that looks a lot like defer.
drewr has quit [Read error: Connection reset by peer]
drewr has joined #zig
KoljaKube has joined #zig
factormystic has quit [Read error: Connection reset by peer]
danyspin97 has quit [Ping timeout: 256 seconds]
danyspin97 has joined #zig
redj has quit [Remote host closed the connection]
rzezeski has quit [Quit: Connection closed for inactivity]
redj_ has joined #zig
cole-h has joined #zig
redj_ is now known as redj
cren has joined #zig
Akuli has joined #zig
dermetfan has quit [Ping timeout: 244 seconds]
nmeum_ is now known as nmeum
cren has quit [Ping timeout: 256 seconds]
cren has joined #zig
<cren> anyerror!<return type> is the same as !<return type>, right? (Replace <return type> with the return type of your choice)
<fengb> `!T` is inferred to be all of the errors actually returned from the body of the function. `anyerror!T` is literally all the errors the compiler knows about
<ifreund> e.g. if the function can only return error.OutOfMemory, !T is the same as error{OutOfMemory}!T
dermetfan has joined #zig
<cren> how does the compiler know about errors? I mean: does it only know the stdlib errors? What if I write my own error?
<fengb> When you create an error, it adds it into the globalset of all errors
<cren> interesting
<fengb> It's a u16. If there's more than 64k errors, the compiler livelocks atm 🙃
<cren> what's a livelock? (I'm guessing it locks up while running?)
<fengb> It locks with 100% cpu
<cren> ouch
<fengb> Busy doing... something
<cren> I don't understand why `_ = try network.init()` is giving me "error: expected type 'void', found 'zig-network.network.error:10:15'"
<ifreund> cren: what's the signature of the function containing this line?
<cren> ifreund: oh, it's just `void`. That'll be it. If I change it to `!void`...
<ifreund> yep, exactly
<ifreund> try foo() is sugar for foo() catch |err| return err
<cren> ifreund: I'm even at that page in the docs, I feel silly for not seeing it...
<ifreund> eh, I think everyone feels silly when learning a new language
<cren> :)
<cren> can I define a function that takes an array of type T as an argument?
<cren> hmm actually that isn't what I want
<cren> I was just trying to make a function to which I could pass arguments that would make up the second argument of debug.print
<ifreund> you probably want to make the function take an anytype argument and then ++ the tuples
<ifreund> e.g. you can do std.debug.print("{} {}\n", .{"hi"} ++ .{"there"});
<cren> my goal was to avoid having to type the "{}\n" bit
<cren> i'm very lazy
keegans has quit [Quit: WeeChat 2.7]
<fengb> The error message is quite confusing
<fengb> I think we've all been baffled at one point or another
<ifreund> ah, your function would be fn lazy(x: anytype) void { std.debug.print("{}\n", x); }
<KoljaKube> cren: Off the top of my hat I'd say that you can't create the format string for that without some sort of dynamic allocation, if you are trying to wrap std.debug.print
<cren> KoljaKube: yeah, the more I think about it the harder it seems
<ifreund> oh but for as many parameters as you want, that's doable one sec
<KoljaKube> I don't know about the internals, but if everything is streamed, maybe you could reimplement it to do what you want
<KoljaKube> But I guess I'll be taught otherwise in a sec :D
<ifreund> fn lazy2(x: anytype) void { std.debug.print("{}" ** x.len ++ "\n", x); }
<ifreund> just had to look up how to get the length of a tuple
<KoljaKube> Oh boy, nice one
<KoljaKube> Forgot about **
<ifreund> ** is handy, especially for putting stuff in arrays at comptime
* KoljaKube makes a mental note
<cren> what does ** do?
<ifreund> "{}" ** 3 == "{}{}{}"
<ifreund> it multiplies arrays at comptime
<cren> ifreund: what do I pass to that function? an array?
<ifreund> cren: a tuple, just like std.debug.print's second arg
<ifreund> lazy2(.{"hello", 5, 0x00, "bye"});
<cren> ifreund: oh, for some reason I thought that was an array. So tuples can have more than one time in them? That surprises me
<ifreund> a tuple is more like a struct with anon fields than an array
<ifreund> and it's not surprising that you thought it was an array, tuples aren't really explained that well in the docs yet
<cren> is that .{<stuff>} the literal syntax for a tuple, then?
<ifreund> yeah, exactly
<ifreund> tuples are a fairly new language feature and there's still some fleshing out to do
<KoljaKube> ifreund: Remember those value-guarding functions we talked about?
<ifreund> KoljaKube: like what odin does with it's "where" keyword?
<KoljaKube> Don't know about that, I started from Kotlin
<KoljaKube> `ensureNotNull(my_optional); useNonOptional(my_optional);` is along those lines I meant
<ifreund> I think odin does what you described
<ifreund> iirc there's a zig issue somewhere as well
<KoljaKube> Hmm, that looks nice, yes. Anyhow, I remembered why I found them interesting in the first place: they are user-definiable and (in theory) not limited to stuff like nullability
<KoljaKube> Looks like odin takes all that a step further :D
<KoljaKube> (hadn't heard about the language until now)
cren has quit [Quit: Swirc IRC client]
<ifreund> I've never used it, just look at it to see what choices it made
<ifreund> personally, Zig fits what I want more
<fengb> Probably Zig’s closest competitor. gingerBill and andrewrk have a friendly “rivalry”
<ifreund> er, better? whatever
<KoljaKube> The nice thing about those clauses in Kotlin is that they can be runtime-checked. Those two links look more focused on comptime
<fengb> Zig doesn’t have runtime polymorphism
<KoljaKube> It's not about polymorphism
<fengb> Er... types don’t exist at runtime
<fengb> So you can’t check them at runtime
<fengb> And type sizes need to be known, although that can be worked around with a pointer
<KoljaKube> You could in theory do `if (isPositive(my_i32)) { var foo: u30 = my_i32; }` and the compiler would know not to complain}
<fengb> Oh you mean type narrowing. I thought we were talking about functions args
<KoljaKube> Again, _in theory_, the groundwork is laid for all kinds of checks that only have effects in the compiler
<KoljaKube> Don't know about the implementation status for more complex scenarios though
<KoljaKube> Still a neat idea I think
waleee-cl has joined #zig
craigo has joined #zig
gruebite has quit [Ping timeout: 256 seconds]
nvmd has joined #zig
Akuli has quit [Quit: Leaving]
ur5us has joined #zig
KoljaKube has quit [Ping timeout: 256 seconds]
dermetfan has quit [Ping timeout: 260 seconds]
nvmd has quit [Quit: Later nerds.]
blinghound has joined #zig
blinghound has quit [Ping timeout: 245 seconds]
blinghound has joined #zig
blinghound has quit [Remote host closed the connection]
xackus has quit [Ping timeout: 240 seconds]