Oddbean new post about | logout
 there is no question that C is more complicated to learn than Go, but Go gives you a lot of teh performance (about 90%, and the main limitations are that Go is not so good at parallelism compared to using pthreads)

i'd also suggest trying C because it's pretty good for writing simple mathematical algorithms with, but the implicit types get messy, and personally one of the things i hate about Go is the fact that the `int` type is 32 bit on 32 bit hardware, and you see this sometimes in code, people using explicit int64 (signed) in a lot of places even though in practice, almost nobody puts serious servers on 32 bit processors 
 oh yeah, and the "int" used in array indexes in Go are in fact 32 bit, no idea if that will ever be expanded, but arrays of more than 4 billion elements are pretty much outside of the needs of a graph simulation 
 I think it's fair to say threading it's an apples to oranges comparison because there isn't a pattern or a standard library in C for threading. So if you need jump into a highly multi threaded or even async, C probably isn't it. Not unless you want to spend a bunch of time implementing the patterns yourself. 

I think as a fun analog, in noscrypt I implemented the concept of a Span taken from C# to help me more safely work with buffers, except with macros and inline functions to make it nearly invisible when compiled. 

> i'd also suggest trying C because it's pretty good for writing simple mathematical algorithms with
Completely agree on this!

>but the implicit types get messy
Also yes, some libraries work well with an int being 8,16,32,or even 64 bits wide without your knowledge. I usually use explicit types but many libraries don't because it can often be easier to trust the compiler to manage sizing correctly for you. That takes more brain power than I wanted to dedicate to noscrypt right now, but I may switch back to implicit types for compat reasons.  
 using the pthreads library would be a bit more performant than Go's concurrency if you can fan out your processing for bulk stuff like what nostr:nprofile1qy2hwumn8ghj7un9d3shjtnyv9kh2uewd9hj7qghwaehxw309aex2mrp0yhxummnw3ezucnpdejz7qgkwaehxw309ash2arg9ehx7um5wgcjucm0d5hsz9mhwden5te0wfjkccte9ec8y6tdv9kzumn9wshsqg8ks058qd0h4485fc9e3naaj5m7zez44ykd8r80cn9nrkm42l677g2aakns  wants to do, and really the flexibility of Go's concurrency is overkill for simple parallel work, it's a little confusing to do it that way, it's more optimized towards event processing for servers, but the design of it was originally created for GUI (newsqueak)

go is actually not so great at parallelism, you can gain as much as 20% even while adding the overhead of an IPC and using single threaded worker processes (at least that was the situation in 2020, not sure maybe they have improved it by now) - but having said that, it's so much faster than for example python or javascript, that losing that last 20% of parallelism is probably not gonna hurt that much, and if you want it scaled up that much, like on a threadripper or epyc or something, well, you'd probably not be using Go, but C and pthread

go is pretty fast for single thread processing, not much slower than C, especially if you don't allocate and discard a lot of memory, walking trees and graphs is cheap, everything stays on the stack/registers

but yes, explicit types are a thing... i ported a hamming code algorithm from C some years back and the hardest part of the process was figuring out the implied bid widths, and this is pretty much par for teh course with C, your use of explicit types is probably a bit uncommon among C programmers

personally, i would remove the distinction in Go where on 32 bit hardware it treats the `int` type as 32 bits... it should just always be 64 bits, except where used in array indexes, this is one area it's implicit, and 64 bit array indexes is a waste of space, ain't nobody got that much memory lol, but it's not a difference that anyone really encounters because Go on embedded 32 bit devices is pretty much not a thing, except for tinygo, which is not really go, though it is go (has more controls for memory management, but still lets you do all the nice interface/dynamic array stuff, and Go's concurrency can even operate on a single thread