ReplaceFile
exists to get everyone else’s semantics though?
ReplaceFile
exists to get everyone else’s semantics though?
Related, note that division is much slower than multiplication.
Instead of:
n / d
see if you can refactor it to:
n * (1.0/d)
where that inverse can then be hoisted out of loops.
This is about the one thing where SQL is a badly designed language, and you should use a frontend that forces you to write your queries in the order (table, filter, columns) for consistency.
UPDATE table_name WHERE y = $3 SET w = $1, x = $2, z = $4 RETURNING *
FROM table_name SELECT w, x, y, z
It’s because unicode
was really broken, and a lot of the obvious breakage was when people mixed the two. So they did fix some of the obvious breakage, but they left a lot of the subtle breakage (in addition to breaking a lot of existing correct code, and introducing a completely nonsensical bytes
class).
Python 2 had one mostly-working str
class, and a mostly-broken unicode
class.
Python 3, for some reason, got rid of the one that mostly worked, leaving no replacement. The closest you can get is to spam surrogateescape
everywhere, which is both incorrect and has significant performance cost - and that still leaves several APIs unavailable.
Simply removing str
indexing would’ve fixed the common user mistake if that was really desirable. It’s not like unicode
indexing is meaningful either, and now large amounts of historical data can no longer be accessed from Python.
The problem with mailing lists is that no mailing list provider ever supports “subscribe to this message tree”.
As a result, either you get constant spam, or you don’t get half the replies.
Unfortunately both of those are used in common English or computer words. The only letter pairs not used are: bq, bx, cf, cj, dx, fq, fx, fz, hx, jb, jc, jf, jg, jq, jv, jx, jz, kq, kz, mx, px, qc, qd, qg, qh, qj, qk, ql, qm, qn, qp, qq, qr, qt, qv, qx, qy, qz, sx, tx, vb, vc, vf, vj, vm, vq, vw, vx, wq, wx, xj, zx.
Personally I have mappings based on <CR>
, and press it twice to get a real newline.
The problem is that there’s a severe hole in the ABCs: there is no distinction between “container whose elements are mutable” and “container whose elements and size are mutable”.
(related, there’s no distinction for supporting slice operations or not, e.g. deque
)
I guess I forgot to mention the other implicit difference in concerns:
When you are a game, you can reasonably assume: I have the user’s full focus and can take all the computing resources of their device, barring a few background apps.
When you are an application, the user will almost always have several other applications running to a meaningful degree, and those eat into available resources (often in a difficult-to-measure way). Unfortunately this rarely gets tested.
I’m not saying you can’t write an app using a game toolkit or vice versa, but you have to be aware of the differences and figure out how to configure it correctly for your use case.
(though actually - some purely-turn-based games that do nothing until user enters input do just fine on app toolkits. But the existence of such games means that game toolkits almost always support some way of supporting the app paradigm. By contrast, app toolkits often lack ready support for continuous game paradigms … unless you use APIs designed for video playback, often involving creating a separate child “window”. Actual video playback is really hard; even the makers of dedicated video-playing programs mess it up.)
The problem with XCB is that it’s designed to be efficient, not easy. If you’re avoiding toolkits for some reason, “so what if I block the world” may be a reasonable tradeoff.
There’s tends to be one major difference between games and non-game applications, so toolkits designed for one are often quite unsuitable for the other.
A game generally performs logic to paint the whole window, every frame, with at most some framerate-limiting in “paused” states. This burns power but is steady and often tries hard to reduce latency.
An application generally tries to paint as little of the window as possible, as rarely as possible. Reducing video bandwidth means using a lot less power, but can involve variable loads so sometimes latency gets pushed down to “it would be nice”.
Notably, the implications of the 4-way choice between {tearing, vsync, double-buffer, triple-buffer} looks very different between those two - and so does the question of “how do we use the GPU”?
1, Don’t target X11 specifically these days. Yes a lot of people still use it or at least support it in a backward-compatible manner, but Wayland is only increasing.
2, Don’t fear the use of libraries. SDL and GTK, being C-based, should both be feasible from assembly; at most you might want to build a C program that dumps constants (if -dM
doesn’t suffice) and struct offsets (if you don’t want to hard-code them).
Even logging can sometimes be enough to hide the heisgenbug.
Logging to a file descriptor can sometimes be avoided by logging to memory (which for crash-safety includes the possibility of an mmap’ed file, since the kernel will just take care of them as long as the whole system doesn’t go down). But logging from every thread to a single section of memory can also be problematic (even without mutexes, atomics can be expensive and certainly have side-effects) - sometimes you need a separate per-thread log, and combine in the log-reader tool.
I don’t remember the last time I used ctrl-C. It’s always select or "+y
.
True, but successfully doing dynamically-linked old-disto-test-environment deployments gets rid of the real reason people use static linking.
DNS-over-TCP (which is required by the standard for all replies over 512 bytes) was unsupported prior to MUSL 1.2.4, released in May 2023. Work had begun in 2022 so I guess it wasn’t EWONTFIX at that point.
Here’s a link showing the MUSL author leaning toward still rejecting the standard-mandated feature as recently as 2020: https://www.openwall.com/lists/musl/2020/04/17/7 (“not to do fallback”)
Complaints that the differences are just about “bug-for-bug compatibility” are highly misguided when it’s useful features, let alone standard-mandated ones (e.g. the whole complex library is still missing!)
I haven’t managed to break into the JS-adjacent ecosystem, but tooling around Typescript is definitely a major part of the problem:
At this point I’m seriously considering writing my own sanelanguage-to-JS transpiler or using some other one (maybe Haxe? but I’m not sure its object model allows full performance tweaking), because I’ve written literally dozens of other languages without this kind of pain.
WASM has its own problems (we shouldn’t be quick to call asm.js obsolete … also, C’s object model is not what people think it is) but that’s another story.
At this point, I’d be happy with some basic code reuse. Have a “generalized fibonacci” module taking 3 inputs, and call it 3 ways: from a web browser on the client side, as a web browser request to server (which is running nodejs), or as a nodejs command-line program. Transpiling one of the callers should not force the others to be transpiled, but if multiple of the callers need to be transpiled at once, it should not typecheck the library internals multiple times. I should also be able to choose whether to produce a “dynamic” library (which can be recompiled later without recompiling the dependencies) or a “static” one (only output a single merged file), and whether to minify.
I’m not sure the TS ecosystem is competent enough to deal with this.
If there’s a .pc
file shipped, pkg-config
can simplify your life by figuring out the flags for you.
The problem is that the application developer usually thinks they know everything about what they want from their dependencies, but they actually don’t.
For one thing: don’t bother with fancy log destinations. Just log to
stderr
and let your daemon manager take care of directing that where it needs to go. (systemd made life a lot easier in the Linux world).Structured logging is overrated since it means you can’t just do the above.
Per-module (filterable) logging are quite useful, but must be automatic (use
__FILE__
or__name__
whatever your language supports) or you will never actually do it. All semi-reasonable languages support some form of either macros-which-capture-the-current-module-and-location or peek-at-the-caller-module-name-and-location.One subtle part of logging: never conditionally defer a computation that can fail. Many logging APIs ultimately support something like:
This is potentially dangerous - if logging of that level is disabled, the code is never tested, and trying to enable logging later might introduce an error when evaluating the arguments or formatting them into the message. Also, if logging of that level is disabled, side-effects might not happen.
To avoid this, do one of:
if
-style deferring, internally or externally. Instead, squelch the I/O only. This can have a significant performance cost (especially at theDEBUG
level), which is why the API is made in the first place.