4 ms·
I can't say I learned much by programming in C, if I even learned anything at all. Mostly I just grumble at the needlessly verbose and complex way of doing some
by Beltalowda 4y ago
I can't say I learned much by programming in C, if I even learned anything at all. Mostly I just grumble at the needlessly verbose and complex way of doing some things (e.g. anything with strings) and get annoyed by the syntax and quirks of the language and surrounding toolchain.
It is of course useful for a whole bunch of reasons, including being able to figure out "why does this do X?", but that's not really "deeper knowledge", IMO.
- stevekemp 4y agoCompared to writing code in assembly language it is a dream, though! I think C lets you think about low-level details of how systems work, strings being arrays of characters with an explicit terminating NUL character, for example. Although again assembly language gives you _real_ lower-level understanding and insights if you use it.
- Beltalowda 4y agoIt's useful to know how things like strings and arrays work and that they're not just "magic", but I don't think you really need to learn C to do that. I understood that kind of stuff long before I did any serious C programming, and knowing C didn't really add much to that. The thing is that I don't want to think about it every time. I "just" want to do X, but instead I need to write a whole bunch of code to handle it all manually. It's useful that this is possible, but a lot of times you don't need it, and some other languages still keep the "common case" easy while still enabling the high-performance stuff C can do. I wish we had C+: C + a few niceties (and not C ++ everything). There's a whole bunch of newer languages aiming at the space C is sitting in, but with a few additions C could be much more ergonomic without having to invent an entire new language.
- AlbertoGP 4y ago> I wish we had C+: C + a few niceties (and not C ++ everything). There's a whole bunch of newer languages aiming at the space C is sitting in, but with a few additions C could be much more ergonomic without having to invent an entire new language. I’ve made a pre-processor for C to add some things I miss, although it is currently limited to what can be done without type information and has to keep compatibility with existing C syntax: https://sentido-labs.com/en/library/cedro/202106171400/ https://sentido-labs.com/en/library/cedro/202106171400/ There is another language called C3 that “is a C-like language striving to be an evolution of C, rather than a completely new language”: https://github.com/c3lang/c3c https://github.com/c3lang/c3c If you have the time, I’d like to hear which things you miss in C. There might be something I did not imagine that could be added to Cedro.
- musicale 4y ago> Compared to writing code in assembly language it is a dream, though C is a something of a high-level assembly language. Of course we could write literal assembly language in C, pretty much. r1 = 0 r2 = 1 r3 = r1 + r2 mem[1000] = r3
- Thiez 4y agoExcept that C targets the C abstract machine, which can't do a lot of stuff that is perfectly acceptable in assembly. Such as reading uninitialized memory, padding, overflowing signed integers, forging a pointer (e.g. for memory mapped I/O) out of thin air, dereferencing null...
- cyber_kinetist 4y agoBy the way, null-terminated strings are not the only way to express strings, it’s a legacy of C that many low-level programmers dislike but need to stick to it because of legacy reasons (every major OS is written in C). All the low-level languages aiming to replace C basically abandoned this approach, and opted for slices instead (ptr + size pair, used in Rust, Zig, etc.) This has the benefit of easier and faster string manipulation (strlen can be O(1) instead of O(n)), as well as better memory safety (can do bounds checking with the size information). The primary reason we are still using and teaching null terminators is because we still have to live with POSIX/Win32 and many low-level libraries written on this platform.
- stevekemp 4y agoIndeed, I remember Turbo Pascal, running under CP/M, used the scheme where strings where prefixed with their length rather than being NUL terminated.
- rofrol 4y agoI thought zig has null terminated string literals. What's the difference? String literals are constant single-item Pointers to null-terminated byte arrays. The type of string literals encodes both the length, and the fact that they are null-terminated, and thus they can be coerced to both Slices and Null-Terminated Pointers https://ziglang.org/documentation/master/#String-Literals-and-Unicode-Code-Point-Literals https://ziglang.org/documentation/master/#String-Literals-an...
- cyber_kinetist 4y agoHmm... after some research it seems that I've misunderstood Zig's situation a bit. Zig has introduced null-terminated string types a couple of years ago, but still encourages you to do most string operations with slices instead. Let me explain: Zig's string literals (which you create with parenthesis like "Hello world!") are null-terminated byte arrays, expressed as the type *const [N:0]u8 (where the :0 tells you that it's null-terminated), whereas the more typical array might be written as *const [N]u8. The reason for this feature is not because the language wants you to use null-terminated strings, but because these static strings need to be stored in the global data section of the ELF executable, and these require you to use null-termination. But if you want to do any mutable operation with this string, you need to convert this into a proper slice (ptr + size). And it seems like Zig developers don't really use null-terminated types that much at the API level, but use it for things like C interop or cases where you really need it for special optimizations. Noting that from the PR that introduced this feature, Andrew Kelley writes [0]: > I think you will find that the Zig community in general (and especially myself) agrees with you on this [null-terminated strings being fragile], and APIs in general should prefer slices to null terminated pointers. Even if you are using Zig to create a C library, and even in actual C libraries, I would recommend pointer and length arguments rather than null terminated pointers, like this: https://github.com/andrewrk/libsoundio/blob/1.1.0/soundio/soundio.h#L795 https://github.com/andrewrk/libsoundio/blob/1.1.0/soundio/so... > That being said, I want to repeat what I said earlier about null terminated pointers: A null terminated array is not inherently an evil C concept that is intruding in the Zig language. It's a general data storage technique that is valid for some memory constrained use cases. I also stumbled on a Real Actual Use Case inside LLVM. The bottom line for me is that null terminated pointers exist in the real world, and especially in systems programming. You can see this in interfaces with the operating system in the standard library... So he acknowledges null-terminated strings can certainly be useful in certain situations outside of legacy reasons, which is good to know. And Zig creating a special type for this shows that a good systems language needs to be designed to accommodate the needs of the outside world. [0] https://github.com/ziglang/zig/issues/265#issuecomment-463374382 https://github.com/ziglang/zig/issues/265#issuecomment-46337...
- epse 4y agoImo the string thing is a bad example, as they don't really have to work that way. Storing length is another solution, but because C is C, the NUL method is quite prominent, if annoying
- tmaly 4y agoeven assembly is essentially bytecode on the modern processors. I think you can eck out more performance, but the time investment is much more.