Live data from Hacker News

An intro to Zig's integer casting for C programmers

lagerdata.com

61–70 of 135 posts

Re: An intro to Zig's integer casting for C programmers

#61
post #45

Earlier quoted context omitted.

C integer promotions are what remains of old computers systems which couldn't handle anything but a 'word'. It result in things highly inconsistent on modern 64-bit machines: For example, char/short are automatically promoted to int or unsigned int when an operation is performed on them, but this doesn't happen between int and long. Simple things like adding two int16_t together to get a int16_t in return is really h…

> adding two int16_t together to get a int16_t in return is really hard Because the first thing people will do is: int16_t a, b; a = (int16_t) ((b * 157) >> 12); and then if b * 157 doesn't promote to 32-bit it overflows in the negative and then the code is incorrect.

You're assuming `int` is 32-bits. The fact that C implicitly promotes to `int` makes it extremely hard to use the stdint.h typedefs without accidentally making platform-specific assumptions.

   uint16_t a, b, c;
   a = 50000;
   b = 40000;
   c = a * b;
This simple code may or may not have undefined behavior depending on the target platform. (it's fine for 16-bit int, UB for 32-bit int, and fine again for 64-bit int)

Numeric promotion means that it's almost impossible to write code that is correct on multiple platforms with different sizeof(int).

Re: An intro to Zig's integer casting for C programmers

#62

Earlier quoted context omitted.

I once collected all of my posts about Ada which do contain lots of links that can get you started. I will not re-post them here, instead you may go to https://news.ycombinator.com/item?id=23808305 . Check out the links under [2]. Especially these ones: https://news.ycombinator.com/item?id=21435869 and https://news.ycombinator.com/item?id=21437498

Thanks!

No problem! You might find this website useful, too, as it is filled with resources: https://www.adaic.org/learn/materials/

Re: An intro to Zig's integer casting for C programmers

#63
post #21

Earlier quoted context omitted.

Ada / spark may be a great thing. But how do people know? Is there a good compiler that one can install for free? Are there a few good and comprehensive books / references / guides, available online for free? If you want something to become popular, give it away . Ideally, push it. At the very least, have a limited free version. Or turn a bling eye to small-time piracy, as many vendors did for a long time. Or make it…

Not sure why you think ADA/Spark isn't free. There's GNAT[0], an open source ADA compiler that's part of the GNU toolchain, a fairly good book teaching ADA and SPARK[1] by Ada Core, and plenty of tutorials. Accessibility is really not the problem. The problem is, Ada is an old language that has many similar problems to C: lack of a good package management story, and a design by committee making language evolution gla…

Your first link pretty much says it all: barebones website 5 years out of date, no docs, no resources, no community links, no indication that this project is even alive. To top it off the project is named after one of the most annoying creatures on the face of the Earth. This is a marketing issue.

The problem for older languages is that the bar for what's expected of a language has risen substantially. A long time ago, languages weren't even expected to have implementations. Today, not only are implementations expected for all major platforms, languages are also expected to run on phones and the browser, include package managers and library repositories, have a language server implementation and editing modes for all major IDEs, be open source with active development, provide extensive documentation on the scale of a book, and also promote a vibrant and active community. Oh, and to top it off, users don't want to pay for any of that. It's just expected, which is why most languages these days only come out of large tech companies that can afford to fund all of the above with no expectation of profit.

Re: An intro to Zig's integer casting for C programmers

#64
post #58

I am curious to know the reasons behind the @as() syntax. What's wrong with "i32 y = (i32) x;"? I look with interest to new languages but after so many years dealing with C, my parser crashes when I see the type after the variable name and at the end of functions declarations. var x : u8 = 5; What's wrong with "u8 x = 5;"? And I don't really like type inference very much (or when it's abused or cannot be avoided). Wh…

remove "pub" from your godbolt. Zig/godbolt is identifying that you're trying to build a full program and so it brings in a lot of the boilerplate necessary to launch a program (for example, the panic handler, stdlib stuff to format strings for the panic handler, etc).

Re: An intro to Zig's integer casting for C programmers

#66
post #38

Earlier quoted context omitted.

I agree that float int conversions are evil. I would make an exception for int to float conversion for literals. When switching from C to Rust I was annoyed by: if x > 0 not compiling, because that's an integer zero, not a float zero! This makes the compiler feel very petty.

To me that seems equivalent to complaining that the following fails to compile: if 0 == "0" ... which is obviously broken code.

The number 0 happily and unambiguously plays a role in many numeric types and algebraic structures, and it’s kind of nice if the compiler can just figure out the type that it should be from context. Comparing a literal 0 to a double should cast to a double, comparing a literal 0 to an int should cast to an int, etc. I would be happy for “(int) 0 == (double) 0” to raise a type error though.

I guess it’s a matter of interpretation: does “x == 0” mean that we are comparing x with the integer zero, or the “zero value” of the same type as x? Numeric code is difficult for many reasons, but something that can make it much more tractable is having the code as close as possible to the mathematics underlying the algorithms, and this kind of “polymorphic constant” behaviour can help a lot, especially for integer literals which unambiguously embed into essentially any numeric type you could think of.

Re: An intro to Zig's integer casting for C programmers

#67
post #58

I am curious to know the reasons behind the @as() syntax. What's wrong with "i32 y = (i32) x;"? I look with interest to new languages but after so many years dealing with C, my parser crashes when I see the type after the variable name and at the end of functions declarations. var x : u8 = 5; What's wrong with "u8 x = 5;"? And I don't really like type inference very much (or when it's abused or cannot be avoided). Wh…

> What's wrong with "u8 x = 5;"?

I believe it makes the parser marginally more complicated. Let's say you had a non-builtin type, "foo". The var trigger immediately declares what's going on. For "foo x = 5;" the parser must either 1) have contextual information that foo is a declared type or 2) wait to notice that there are two identifiers side-by-side and then resolve that this means "it must be a variable declaration".

Honestly, C and C++ are very much in the minority for choosing this syntax. Coming form pascal, I remember finding this syntax to be annoying 20 years ago, so it's my bias to believe that this is just internalized pain for C devs.

As for the type coercion with the () operator... well, C is infamous for "spiral types". Typecasting complicated things in C, like, say, an array of pointers, can get scary as hell.

Re: An intro to Zig's integer casting for C programmers

#68
post #29
post #9

Earlier quoted context omitted.

C programmers are well known to refer to such programming safety as straighjacket since the Pascal days anyway. There was more than enough time to learn why it was the right option to start with.

Rust does go overboard though, e.g. indexing requires `usize`. You either use `usize` for all your integers, or you end up with a cast-salad. arr[i as usize] This is actually risky, because even when you only meant to extend, you can also accidentally truncate or change sign. `as` does all of these things without a warning, and mixed with type inference it can easily lead to surprises. Rust makes it worse by insistin…

The Rust approach of having all indexing being unsigned has been extremely annoying for programming algorithms which need to do interesting indexing patterns like walking backwards through an array while indexing into another: the fact that “i >= 0” can no longer be used as a loop condition is quite exasperating. It means other more complicated indexing or looping approaches need to be used, and when showing code to coworkers (mostly mathematicians), they puzzle over this for a while before asking “why not just use i >= 0”? It’s not just this case - doing index arithmetic in general is vastly complicated by the fact that it’s difficult to detect idx I think unsignedness on array indices is one of those places where the “make invalid states unrepresentable” mantra has gone too far: yes it’s nice that theoretically the whole 64-bit index space is addressable from a byte array based at 0, but in reality -1 is just as stupid and invalid an array index as 2^64 - 1 for pretty much every use-case. What we gain is negligible; what we lose is a lot of sensible code for dealing with index arithmetic.

Re: An intro to Zig's integer casting for C programmers

#69

Earlier quoted context omitted.

> Make something idiot-proof and the world invents a better idiot. Sure, but if you only ever give people safety scissors then you're severely limiting the kinds of things that they can build. You have to let people who know what they are doing be able to do what they need to do, so you have to be able to turn the runtime safety off. Zig can do this at the scope level.

I don't understand why there aren't any solutions like this. Why aren't there any languages with a good garbage collector but also let you turn it off and work with memory manually. Maybe there is and I don't know of it? Maybe garbage collected languages and manual memory languages require different design? I don't know.

Nim is built like this. The gc is opt-in by type and manual memory management is simple. All other types are stack allocated by default.

The new gc is pretty much compiler assisted scope managed smart pointers as well. Also when using the gc you can build your own types with custom create/free/copy/move operators to do what you want without worrying about a stop the world gc.

Using the arc gc pretty much compiles down to what you'd do manually. For cycles you can use the orc gc, again it's all opt in.

I find this a great balance of productivity and performance, where it's easy to have high control when you want it, and still get good performance when you're not bothered.

Re: An intro to Zig's integer casting for C programmers

#70

Earlier quoted context omitted.

C integer promotions are what remains of old computers systems which couldn't handle anything but a 'word'. It result in things highly inconsistent on modern 64-bit machines: For example, char/short are automatically promoted to int or unsigned int when an operation is performed on them, but this doesn't happen between int and long. Simple things like adding two int16_t together to get a int16_t in return is really h…

Not my idea, but: expanding all values used in expressions to "native word size" (e.g. int64_t on modern machines), and only treat "bit width" and "signedness" as load/store attributes doesn't seem like such a bad idea. The problem seems to be that (AFAIK) C stopped at 32-bit integers.

I agree, both choices are fine as long as they are consistent.

One issue with expanding all values to native word size is that this would manly benefit _very_ old hardware: modern CPUs are as fast directly manipulating any int size as they are manipulating "native word size", or even worse because vector instructions usually manipulate twice many int32 per cycle than they manipulate int64 (and twice many int16 as int32), even if not every code can be vectorized.

Post reply on HN