HackerTrans
TopNewTrendsCommentsPastAskShowJobs

demosthanos

no profile record

comments

demosthanos
·в прошлом году·discuss
It's from The Practice of Programming, published 1999. Not a lot has changed in debuggers since then from what I can see.
demosthanos
·в прошлом году·discuss
True, but then you're still left stepping through your breakpoints one by one.

Printf debugging gives you the full picture of an entire execution at a glance, allowing you to see time as it happened. The debugger restricts you to step through time and hold the evolution of state in your memory in exchange for giving you free access to explore the state at each point.

Occasionally that arbitrary access is useful, but more often than not it's the evolution of state that you're interested in, and printf gives you that for free.
demosthanos
·в прошлом году·discuss
Your framing makes it sound like the log is worse in some way, but what the log gives you that the debugger makes you assemble in your head is a timeline of when things happen. Being able to see time is a pretty big benefit for most types of software.

I can always drop an entire state object into the log if I need it, but the only way for a debugger to approximate what a log can give me is for me to step through a bunch of break points and hold the time stream in my head.

The one place where a debugger is straight up better is if I know exactly which unit of code is failing and that unit has complicated logic that is worth stepping through line by line. That's what they were designed for, and they're very useful for that, but it's also not the most common kind of troubleshooting I run into.
demosthanos
·в прошлом году·discuss
There was a good discussion on this topic years ago [0]. The top comment shares this quote from Brian Kernighan and Rob Pike, neither of whom I'd call a young grug:

> As personal choice, we tend not to use debuggers beyond getting a stack trace or the value of a variable or two. One reason is that it is easy to get lost in details of complicated data structures and control flow; we find stepping through a program less productive than thinking harder and adding output statements and self-checking code at critical places. Clicking over statements takes longer than scanning the output of judiciously-placed displays. It takes less time to decide where to put print statements than to single-step to the critical section of code, even assuming we know where that is. More important, debugging statements stay with the program; debugging sessions are transient.

I tend to agree with them on this. For almost all of the work that I do, this hypothesis-logs-exec loop gets me to the answer substantially faster. I'm not "trying to run the code forwards in my head". I already have a working model for the way that the code runs, I know what output I expect to see if the program is behaving according to that model, and I can usually quickly intuit what is actually happening based on the incorrect output from the prints.

[0] The unreasonable effectiveness of print debugging (349 points, 354 comments) April 2021 https://news.ycombinator.com/item?id=26925570
demosthanos
·в прошлом году·discuss
> To these people, if it's not exposed as a API call it's just some opaque blob of code that cannot be understood or reused.

I think this is correct as an explanation for the phenomenon, but it's not just a false perception on their part: for a lot of organizations it is actually true that the only way to preserve boundaries between systems over the course of years is to stick the network in between. Without a network layer enforcing module boundaries code does, in fact, tend to morph into a big ball of mud.

I blame a few things for this:

1. Developers almost universally lack discipline.

2. Most programming languages are not designed to sufficiently account for #1.

It's not a coincidence that microservices became popular shortly after Node.js and Python became the dominant web backend languages. A strong static type system is generally necessary (but not sufficient) to create clear boundaries between modules, and both Python and JavaScript have historically been even worse than usual for dynamic languages when it comes to having a strong modularity story.

And while Python and JS have it worse than most, even most of our popular static languages are pretty lousy at giving developers the tools needed to clearly delineate module boundaries. Rust has a pretty decent starting point but it too could stand to be improved.
demosthanos
·2 года назад·discuss
It's a lot more complicated than that. What constitutes a human right is deeply tied up in questions of ethics that are not settled and have no universal acceptance even within a single culture. Any given person will have deep feelings about the human rights that their ethical framework demands, but those deep feelings will often contradict the deeply held feelings of other people.

This means that which ethical framework we as a society use to decide what counts as a human right is an inherently political question: it's a decision that we try to make as a society in as nonviolent a manner as possible.

And before we get too far off the deep end, I want to note that both sides of the aisle firmly believe that the other side ignores fundamental human rights that their side respects. This is what happens when good people operate with completely opposite ethical frameworks, and we won't get anywhere by just shouting that our framework is the only valid one.