HNHacker News
TopNewBestAskShowJobs

optionalparens

297 karma · joined October 25, 2015

Fuck you stupid webshits
submissionscomments
optionalparens··on C for Python programmers (2011)
Firstly, let me qualify all of this by saying I try to be a true polygot and use the best tool for the job. Among my regular languages the past few decades include C, C++, Lisp, Java, Clojure, Smalltalk, Python, Ruby, C#, Haskell, Rust, and many more. As such, I have no attachments to any particular language.

C++ and C, while both using the letter C, are for all purposes, entirely differently languages with different goals. Use the one that meets your goals best. While I can agree that K&R is outdated in some areas, there are still plenty of reasons to learn and even use C. If for no other reason, some of the most popular, active, and most used code bases in the world are written in C.

C is essential if you want to understand a lot of the ecosystems around you, fix them, interact with them properly, and maybe one day contribute to or patch them if necessary. I know some people will argue that if they know C++ (or programming in general) they can read C, but hands-on experience is the only real way to learn. You will not know why things are done or recognize when they are done poorly/incorrectly. Moreover, C is a great teacher of how things work, and sometimes also how not to do things. To be ignorant of C is generally to be woefully unaware of how a huge part of a lot of the software you probably use works.

I worked/work in game programming, distributed computing, AI, and many other fields. I find C to be extremely valuable in all fields I have touched and at home and at work. If nothing else, learning about memory, byte ordering, alignment, packing, bit manipulation, etc is a huge solid base. C++ can teach you a lot of that too, but it deals with certain issues on fundamentally different levels (especially modern C++) and has just as many potholes and here be dragons areas. It is true that I don't start as many new projects in C as I used to, but it doesn't stop me if lets say the main thing I need to do is interact with something already in C/embedded, or have a certain level of control that C affords me while being able to also hire people that can work in it (factors when evaluating project constraints).

One argument I consistently hear with regard to C that you hint at is that if you learn C first, before C++, whenever, it will somehow taint you. I would argue that with every language, you are not learning the language if you do not how to write programs in it idiomatically, or even when to counter-balance idiomatic code with code that does what you need to do (ex: boost performance or other tradeoffs). At that point, you are not a programmer but a parrot or like someone who memorizes math formulas but can't apply them.

Programming is not regurgitating countless lines of syntax, it is critical thinking, problem solving, creativity, and many more things. Learn C, and learn other languages. Do not listen to anyone who tells you to learn any particular languages. Match the language with your task, problems, and other constraints. When in C, do C. When in C++, do C++. When in Python, don't do C. And so on. It's really not that hard for anyone experienced.

optionalparens··on George Hotz cancels his Tesla Autopilot-like ‘comma one’
I assume he was just visiting for manufacturing purposes.

What's interesting in China is they have in the past executed people for white collar crime in addition to regulatory officials as well. This though can happen for a variety of reasons unrelated to regulation, rather corruption, being in a rival faction of the wrong people, etc. Anyway, I am not saying it happens a lot or every day, but rather it seems tolerance with regard to regulators and corporations is not necessarily unlimited, especially depending on who's pockets you are lining and where you are from.

https://en.wikipedia.org/wiki/Zheng_Xiaoyu

optionalparens··on George Hotz cancels his Tesla Autopilot-like ‘comma one’
Reminds me of wanting to buy a TV without all the "smart" stuff. In that situation modularity is preferred by most people with at least minimal tech-inclination. I actually encountered some cases of manufacturers charging more for a lesser, non-smart panel.

A car is a bit more complicated to leave stuff out I am sure and the volumes far different. It would likely require at least more resources to have separate parts of lines for some of that as well as different check procedures as so on. But like you said, paying more could help offset that, though it's a gamble for the manufacturer.

I'm more in the camp of please do not release anything driving a car until you guys can figure out how to secure basic software, keep websites running, parse input properly, and so on. In other words, I'd rather them wait decades if that's what it takes.

Personally, I'd rather be killed by a person rather than a person's dumb choice trusting technology. What concerns me in all these situations is that I did not at any point agree or vote to allow someone in a self-driving car to drive on the same road as me. Until they can mathematically prove 100% it is safe in all conditions and situations, I'm not buying things like "driver assist" if a big part of the justification is that AI is better than a human driver (if so, then why assist?). Others may disagree, so be it - I'm a weird guy. I also hate cruise control. And fat-free ice cream.

optionalparens··on George Hotz cancels his Tesla Autopilot-like ‘comma one’
NTSB has awesome investigators. Some of the smartest people I've met and worked with in my life. They are very serious and dedicated, while having to put up with a lot of roadblocks, nonsense, and other issues from both corporate America and other government agencies.

Can confirm at least though many years ago, the internal NTSB IT staff/programmers/DB were a joke. I guess that's just government though and like much of government, they relied a lot on outside contractors. For years they were a ColdFusion shop, so I'll let your mind start there.

optionalparens··on New MacBook Pro Is Not a Laptop for Developers Anymore
Touch typing or not, I think you are missing an important point here with regard to programming - tactile feedback. Doubly so with anyone that uses mechanical keyboards like me.

For example, you may not know where the "f8" key is on your keyboard, but once you look down and locate it, you won't have trouble repeatedly pressing it, accurately, with velocity. A good example of where and why this pattern happens is debugging. A lot of IDEs and editors are setup by default to use f-keys for debug or other ancillary functions like build, specific menus, etc. I believe IntelliJ and Visual Studio in at least a few default setups and versions did this.

More specifically, I can't imagine pressing a touch button possibly dozens of times, sometimes rapidly to advance through a bunch of break points, set new break points, eval things, etc. It is true you could just map these to other keys, but that becomes an issue with anything that is using default key maps for functions as I describe. Additionally, touch buttons promote people to start using more and more keyboard chords as they start shuffling around things in their keymaps, which a lot of people dislike. I'm an Emacs and IntelliJ user primarily, so the former and my arthritis in my hands are well acquainted with regard to keyboard chords and complex mapping sequences.

I have not used this keyboard obviously, but it seems to me from my experiences using similar tech that this is only good for much lesser used macro-like or launch actions. Useful still, yes, but I don't think it is a 1:1 replacement for function keys. I said it in another article and I'll say it here, I don't think this keyboard setup is aimed at programmers, but for most consumers it is likely just fine as much as I hate it. As for value added, that's another discussion.

I do know that if I ever buy or am forced to use one of these, it will always be with my own keyboard. I don't mind the chiclets as much as some people, but at home or the office I use external monitors and mechanical keyboards whenever I can.

optionalparens··on Anti-Aging Startup Raises $116M With Bezos Backing
Somehow this conjures up the image of this Metalocalypse episode which I think sums it up perfectly:

https://www.youtube.com/watch?v=msGvEtmR970

"We can't die." And of course, don't call it Anti-Aging, please, call it "Hamburger time."

- Nathan Explosion

I hope I live long enough to eat my words or see this startup fail. Is that not the only thing to say at the investor meetings?

optionalparens··on MacBook Pro
Looking at the various missing keys and the touch strip, I couldn't help but laugh and cry. Less is more, right? I think we all know this is aimed at casual users, but it's still fun to poke at it.

The first thing that came to mind is any time now that I walk into a coffee shop, if I see someone passing themselves off as a programmer on a new Macbook, I'll know they are just screwing around or otherwise extremely angry (and should not approach). I guess carrying around your own keyboard is going to be more of a thing for people who like to work outside the home/office. As an Emacs user and someone who spent at least some time in Vim and Vi over the years, wow, I can't imagine the inner rage of some people I know if they tried to use this.

The other thing I thought of is hasn't this quite often been a problem for other people who tried similar approaches? For example, we tried the UI with not looking at the main screen with things like the WiiU, did we not? Obviously gaming is different than productivity, but still, the screen is the primary focus. Could we also not just throw dynamic UI like this on in other ways?

A few I've seen/heard of or could be a future tech:

* Remapping an icon or otherwise minimal custom glyphs/text per key.

* Remote style. Ex: Second display like they had with Vista or other things, but via iPhone or other devices - put it next to you, in front, whatever, boom - extra contextual touch screen. Apple even does this for many apps like Logic Pro X.

* Perfecting tactile response better and using a full dynamic keyboard like on some laptops out there right now (but with more mechanical response). Obviously easier said than done.

The problem with all this is I wonder who is looking down so much or wanting to look down. If you have time to look down, is it really such a problem then to use the OS UI to get the same thing done?

Probably the only time most people I know that can actually type decently tend to look down at a keyboard is to orient themselves again in some way. I know sometimes when I switch languages/locales on my machine to type in some other languages, it takes me a second depending on the language. But this tech doesn't help at all with that except giving me a button to flip, that is already a keyboard chord anyway.

optionalparens··on Applying the Linus Torvalds “Good Taste” Coding Requirement
Things like FOREACH are good sane defaults, so the justification only happens based on what you are doing like in the performance example.

IQueryable actually is a superset of IEnumerable (implements it - https://msdn.microsoft.com/en-us/library/system.linq.iquerya...). It is generally useful if you want the laziness and ORM/ORM-like features. If you are using LINQ with SQL, then it would be better to return something like that for many use-cases. IEnumerable is good for general use of course and when you want to make the assumption that you "don't need" all that stuff which is pretty good one for more general cases where you just want read-only results or lazy read-only results (via things like yield).

I agree about potential. Nested FOR and IFs though raises that potential hugely. There is rarely a reason to be nesting more than a few levels deep. In many decades of programming, of course I have deeply nested, yet I have refactored it each time. I have managed to avoid doing excessive nesting the entire time as have most of my colleagues. I am sure someone can find a piece of code somewhere written for something that simply cannot be refactored well or justifies itself otherwise, but I'm not afraid to say statistically that is easy to avoid and hard to justify. I think the nesting issue just raises a bunch of flags including: performance, composability, reusability, clarity, maintenance, and cloaking. So in that sense I do feel it is what you describe as an anti-pattern more than a code smell.

optionalparens··on Applying the Linus Torvalds “Good Taste” Coding Requirement
It sounds to me like you also need to start focusing on atomic functions and abstractions more in general. Your functions should do one things as I mentioned.

Regarding "map," "reduce" is probably the one you want to learn first because you can express many functional constructs like "map" in terms of "reduce."

As a general word, parsing command lines almost always tends to be ugly. My general advice here would be to use the built-in stuff or at least a well-used library as much as possible. If you are finding that you are doing a lot of work yourself or using reg-exs that you made, that's often a side that you are doing something wrong.

Anyway, lots more but I don't want to overwhelm. Good luck!

optionalparens··on Applying the Linus Torvalds “Good Taste” Coding Requirement
Yes, in part what I was saying that in some cultures, people are more openly critical. It just is accepted, and no one gets too offended unless they are from another culture. What you are saying about the inability in US/Canadian culture to be upwardly critical or even critical sideways is entirely true. It is also such a silly thing and really makes the workplace unpleasant for many people, more than someone calling my code shit might do.

As someone who grew up in multiple cultures and lived in other cultures (Toronto, Canada among a few others), I see all too clearly what it means to cross or run-up against cultural boundaries. I've had to explain to girlfriends (outside my culture) for instance not to get offended by my family (non-American) and the things they will say. Quickly, they come to realize that despite the sometimes harsh sounding words, culturally my very blunt family is much warmer than anything they encountered before.

I am also well aware of what criticism means in different cultures and workplaces and I do not struggle with what you described. Your advice about keeping all that in mind is solid from a practical perspective. What I am saying has nothing to do with advising or advocating people to be like Linus or like me. Rather I am saying a few important things - understand the value of bluntness, the reasons behind it, don't be harsh for the sake of being harsh, pretending is silly, and that I am a firm believer in honesty.

I do value knowing what the culture norms are, but I try not to let myself be entirely bound in life by them. I have worked long enough and put myself in situations not to work with people who make me play stupid games or diplomatic twister. People should not discount the value of being direct just because it is against their cultural norms. Further, they should see that people from other cultures or other mindsets might have another point of view worth considering. As a result of just being honest, I find in most situations my communication is perceived clearly. I know this because people tell me exactly that and the results seem to match.

There was an interesting article recently in the NYT or Washington Post or something else big about the UN Ambassador for Israel and what gets said to him from enemy countries behind close doors (nice things, blunt things) vs. the crazy rhetoric some of the same ambassadors use when addressing what he calls the "public UN." In part, one of the points he was making is that the real work was getting done behind closed doors and the rest was mindless gesturing and show for the people back home in various countries.

Regarding Linus specifically, what he says can be taken (and is) sometimes as harshness for the sake of it. That does not mean there is not passion, value, truth, and other things to be found. Notice though that the truly valuable things Linus says in harsh ways are nearly always backed up by facts. If Linus says someone's code is stupid, often he points out exactly why and where instead of wasting time trying to be diplomatic about a bad commit. Taking this to the extreme where you don't provide any reason, feedback, and facts is a big problem. People who do this are not being honest or blunt, they are just being jerks and there lies part of the difference.

Perception is important and that's something people forget. I get that people are sensitive, caught up in their culture, yet at some point I would advise people to think with their brains and grow up. People like to do the same thing I described in the UN - gesture using their status, position, titles. That is a dumb thing that stands in the way of getting things done and what many people would perceive as being a good person. If a CIO wanted to fire me because something I said hurt his/her feelings, that's fine with me and not a place I want to work. I would never purposely say hurtful things to someone, at least things that were not true and certainly not without a concrete reason. My view though is a bad prescription for many people, so it's important to also understand that.

It's also worth noting that there is a time and a place for criticism, which is not all the time. More often than not, instead of whining and blowing up at someone, the situation will correct itself if no one pretends or lies to provide encouragement otherwise. At some point you may need to still intervene, but it is contextual. I'll never tell someone who is doing a bad job a bunch of positive things to encourage them for the sake of it. Likewise, when they start doing an actual good job, I will thank them for it. Linus perhaps could use a little more positive reinforcement. I guess he's OK with how he is, so be it.

I am not afraid to sound insulting here by saying that I think it's a sign of low intelligence if you cannot step outside of yourself at times. Obviously it's hard to do this all the time. People really get so caught up in doing what is expected rather than thinking for themselves. This conjures notions of "sheeple" and living a false narrative. I find these things far more revolting than what anyone could say to me with simple words, other people believe otherwise. I learned long ago there is no way you can make everyone like you, but you can respect everyone at least on basic levels of behavior which does not necessarily mean bowing to their cultural norms and emotions, rather simple, basic humanity.

You mention some examples of social tap dancing. While doing consulting, I had to become the master of this and it's rather a necessary skill in this world that I hate. What people are doing by saying things like, "That doesn't look right to me" is usually lying by omission, acting passive aggressive, or simply communicating poorly by garbling the message. To be honest, this sometimes really annoyed me in Canada when people would pass-off passive aggressive behavior as "polite" behavior. Of course my own culture skews this perception and most of the time. My solution was to take my own advice - understand their point of view, don't be offended, and move forward to what's real.

Generally, I try to always provide facts, reasons, clarity, and to keep calm. I expect the same back, as it should be. I would rather live a good, honest life and not live in a fantasy world. One semi-effective test is that if you have to ask yourself if you are being an a-hole, you are the a-hole. Surprisingly, I have only actually yelled at anyone seriously once in my career and it was related to something just about anyone would react the same (racism). Being honest and blunt doesn't mean you have to treat people poorly, yell, or go out of your way to be negative. On the contrary, I tend to compliment people more because I am not afraid to be open.

I find being open breaks down a lot of important barriers at times. In my personal life, this often leads to a lot of "Thank yous" and being the go-to friend for advice, confessions, problems, and more. In the workplace, people feel comfortable bringing tough and embarrassing problems to me because they know they will get an honest and constructive answer. I often felt crippled at points in my career when I got polite, useless feedback. I can't express how many problems in life or programming I have solved by simply telling it like it is. Quite often, it has nothing to do with dropping f-bombs. Sometimes I just tell someone that I feel stupid and need help, and I am happy when others reciprocate. As you can see, this is probably one area where Linus and I differ, but I can't help but laugh at the reactions he gets from ridiculous people that don't want to admit their own faults. I have many faults and I freely admit them because I want help.

If I had to actually give a piece of advice here, it would be to just be yourself and figure out what you value. Everything you do should be working towards that. If someone stands in your way, don't run them over, just put yourself in a better position - find a new job, move, cut them off, be the better person, prove your points with facts, do whatever you need to get past it while staying a good person. Lying to yourself is a hard thing. Being critical is not being cynical, it is being honest if you approach it with a clear mind. This is all often at odds with tech culture and it has admittedly hurt me in a few cases. But I feel alright with myself and that is success for me.

optionalparens··on Applying the Linus Torvalds “Good Taste” Coding Requirement
There are multiple alternatives to switch (or if) statements and I would generally agree switch statements are mostly a code smell. As one posters described, using the fall-through behavior is more what justifies it and the real difference. I know you asked for ELI5, but let me give you some options to think about how you code on a broader level and how to eliminate both if and switch or at least improve them.

If you think of a switch statement as a pattern matching construct, then you will realize there are many, many alternatives in any programming language, including Python. For instance, the dict method works, as can anything that operates a collection-oriented data structure. For example, you could just as easily loop on a list and do this too, but for most lists this would require a worst case of O(n) iterations where n is the size of the list to match, thus a dict is better. A dict would not work if you want fall-through since you would only be matching on a single key usually, unless once again you do lookups of multiple keys (dict still wins). But a list would support this fall-through behavior with minimum effort and a small list would preform alright.

If your usage is lets say more sophisticated than a key lookup, there may be alternative data structures that you can use to achieve similar results (b-tree, red-black tree, skip list, etc.) though that is of course getting further from the usual behaviors of switch statements.

A functional way to go about it would be to reduce or fold on some collection. If you think about the items that don't match, they wouldn't add anything into the final reduction much in the way map/reduce works traditionally. Many times this would just consolidate the entirety of the function you are calling the switch with the result it is producing. Generally, I'd encourage thinking of writing code that operates on data and thus tends to make good reduce of things like reduce, map, filter, etc. as this often simplifies things and in some cases can actually lead to nice performance if done right. It also tends to force you to write things atomically, with less side-effects, and as pure functions. One of the problems people have with if-statements is they end up burying unrelated concerns or bug-inducing side-effects in each if/else or each branch. This code smell is easy to detect by simply pretending you are looking at new functions for each piece of code under an if/else or case and seeing if they are returning the same "type" in general sense of thing, how much there is in common between each piece, and if they are doing 1 or multiple things each. Most of the time, you are really doing the same thing with one slight difference like an input parameter, and you never really needed an if or at the very least, it could be handled differently. If you are doing more than one thing per if, it often means you are doing too much. Furthermore, you should test that if you were to repeatedly pass the same data to each, would you get the same result?

Another way of handling this is to use multi-methods. Note that in truth, it's the same as above because all you are doing depending on your implementation is pattern-matching. It just depends if your behavior is match one or match multiple (fall-through-like). Python can use attributes to do multi-methods among a few other ways. It's been awhile and mostly I'd avoid using them for performance reasons, but it's another option when thinking of more advanced ways to get rid of switch or if constructs.

In general, it's worth noting that in many languages such as Python, though ifs/switch might be ugly, they can often perform pretty well. It is also worth knowing that if/switch are not very good for functional styles sometimes. Making lists or dicts or other constructs is not always free, or slower/faster so it can sometimes just be a balance between performance, clarity, and composition.

Hopefully that gets you thinking and is not too confusing. A bit exhausted so I'm not thinking my best, though I think I am sending you down a track to explore to help you grow.

optionalparens··on Applying the Linus Torvalds “Good Taste” Coding Requirement
I get what you are saying and I agree somewhat, but there are also some lessons to be learned from Linus and things to consider. I especially agree that many lesser talented people use his behavior as a justification for their own. I disagree that at least some of his lessons or behavior is detrimental.

A good realization in life that many of us have is, "Most people are wrong about most things most of the time." This feels sometimes like it applies by an order of magnitude to programming. I think Linus has a style that deals with this reality head-on and it certainly is not for everyone.

One needs to perhaps not be exactly like Linus, but draw some insight from what he does. First, he is bluntly honest with people and there is virtue there. You can argue there is a polite way to be honest, yet sometimes I wonder if I have found it. For huge parts of my career I made my life harder or even self-sabotaged myself by being overly polite to people. I was always assuming (and often still do) that I am wrong and they are right. Further, I give people the benefit of the doubt, try to help them save face in front of others even when wrong, and hear them out before making judgements. It sounds solid and is many ways a healthy attitude for life in general as well as programming.

The problem that arises is that people are people. It is true that people will take advantage of you. It is true sometimes if you give them an inch, they will take ten. It is true stupid people often get ahead. More often the answer is simply people don't get the message.

You can sit and do a code review with someone, ask them politely to do something, send an email, have a lunch chat, whatever, and the message still does not get across with most programmers. You can say that is bad communication or "my fault," but actually I am speaking more about what I observe rather as a whole than my own personal experience. I have had the privilege of working with best friends for small parts of my career, and even then this was an issue. I can't imagine people with better textbook communication than we did, but maybe what we needed was more Linus-style communication. Sometimes the advice or knowledge is beyond colleagues, and they'll even say, "Yeah, oops, I know you said to do X, but I did Y, my bad." That doesn't help you in project and getting things done, especially if it means minimum someone spends time to fix mistakes they know they should have never made.

If you are direct or even a bit abrasive, there is no ambiguity. I grew up in two different cultures side-by-side and traveled the world at various points, living abroad for periods too. Without providing too much PII, I will say that my experience with American culture is that it is very polite, understanding, apologetic (Canadians get this rep.), relatively open, and welcoming. People in American workplaces are on the one hand uptight, more wound up, extremely dishonest, very opportunistic, melodramatic, and a host of other negative traits. On the other hand, Americans are very precise, thoughtful, at least feign listening to you, clever, and methodical. Compare that to another culture that I'd describe as masters of improv, extremely practical, open, honest, and yet sloppy, self-centered, arrogant, overconfident, and disorganized. Neither culture is better than the other, and like Linus, his style just represents one view point of dealing with programmers that is not really better or worse than most others that work.

I will say that in the second culture I mention, things get done faster for certain types of work. The openness aspect also really matches a part of what Linus does. People tell you exactly what they think of you. Sometimes it's really hurtful such as telling you that you look "fatter" one day vs. another. They don't think of it as malicious though because from their perspective, they think something is wrong and they are trying to help. By pointing out you look like you are gaining weight, you might be surprised to know what is really going on is they think you might be sick and want to take care of you. They think you might be eating bad and want to feed you better food. Sometimes, sure, they are just being dicks.

One can think of what Linus says as just a philosophy that won't work for everyone. Someone telling you exactly what you did wrong and not trying to be diplomatic, cute, or passive aggressive about it ensures the message is clear. It helps you in that you may never make that mistake again. There is no ambiguity hopefully and you either do what he says or decide all of it is not worth your time. Playing games, working people with you do not like, pretending to be nice, and blindly following cultural idiosyncrasies are not things I personally enjoy. Some people need those layers of protection or to live a life with those things, and that's fine I guess and equally OK if I decide not to for myself.

I personally cannot work in an environment like most of corporate America anymore or even startups. I need people to be "real" with me, and to learn non-obvious things. I need to be constantly improving, not patted on the back and stabbed in the back by that same person. I want to be stabbed in the front. Of course I realize for many people that might be soul crushing and too much.

The problem I think is that people are misinterpreting what is going on here. Using curse words at everyone for the sake of cursing or yelling for the sake of yelling is not the message. Nor is one true style of coding. To me, his message in part is "Be honest, be direct, be specific, and be clear." He has one clear direction for most of his projects and expects people to follow it or go home. IMO, this is what many software projects need - good, unwavering, solid leadership. It usually doesn't work with a pure democracy because no decisions, at least not the heard ones are made. I look at committees like the W3C and others and see how long it takes to produce output, how much fighting, etc. I look at github issues and see the long threads of people trying to fake politeness. No thanks.

An ignorant tyrant isn't what is needed either. This is where it gets hard. If there was one style for all projects, we'd use it for all projects. Sometimes democracies maybe do work for small projects. Sometimes the real leader is not the person identified in charge. It takes some luck to have what Linus's projects have and the same leader who is good for one type of project is not good for another. I am 100% certain Linus would fail leading many projects.

As for Linus WRT to the software pantheon, you'd be surprised by what I just wrote to note that I don't really care about him. I do not have heroes or believe in hero worship. Moreover, although I use and value Linux, I do not actually like it and I am somewhat unhappy it exists (but happy vs. Windows lets say). I simply use it because it is better for many of my use-cases than what is out there. That won't stop me from pointing out all the legacy warts and wondering if all this time, money, and effort would not have been better spent on a new OS with a new philosophy that did not carry over the ton of anachronisms and design mistakes from Unix and the surrounding community. I do not even consider most of what is in Linux that interesting or innovative, but I am still glad it exists and most of all can easily appreciate the pragmatism of bringing Unix to the home and affordable business world.

Anyway, look at things for what they are and separate that from your personal beliefs, and it will help you learn even more.

optionalparens··on Applying the Linus Torvalds “Good Taste” Coding Requirement
For loops, even in C# are used in performance sensitive contexts. I believe things have changed in versions of .NET and if you're using things like Mono that also have its own versions.

Foreach generally (or used to) generate more garbage/allocations. Foreach against some types in some versions of C# (ex: structs) produces no allocations. There are also some ugly mutation related things you could do using for instead of foreach, but I'd call that bad code.

The same things are true on many platforms - foreach is generally preferable for non-peformance sensitive code. In some languages and libraries, foreach constructs will do things similar to auto pointers or reference counted pointers, which makes them safe enough, but also slower. The point is that foreach can take up more memory, cause garbage, or cause allocations/free on some platforms and languages which is not always desirable. For is therefore a better choice if you don't want this behavior. Mostly though, using for instead of foreach is micro-optimizing in these cases. Where I'd usually do it is somewhere critical in my code, like something called a lot per frame game loop for example. If I caught someone using a foreach that generated lots of allocations and is called a lot of times in these contexts, I'd probably kill them (and have).

So in short, I guess I'd agree that "many" people would do it, but it's context dependent which include performance goals, target platform, language limitations, and more. Mostly, it's better to just write the code that is safe and works, and go back and fix any bad decisions like this. If it's obvious though, I don't have a problem with the optimization from beginning.

optionalparens··on Applying the Linus Torvalds “Good Taste” Coding Requirement
Like most things, it's all contextual. Were I your manager and we were working on a business app, this might pass code review just fine or I might even suggest what you did here if you had showed me the original.

Another piece of context in a business app might be - "Do we need these values now or later?" That is, should this be lazy, stream results, something like that? I am assuming this is supposed to be C#, but still speaking somewhat generally. You might need to instead yield rather than looping and returning an intermediate list. Better yet, I'd also look for you to return something like a read-only list (ex: IEnuemrable in C#) since this is a query result and that can be done with the first version.

Unfortunately if we had been writing a game though lets say, I would have failed you miserably for the latter version and added 1 mental strike to the "send you packing" count. Why? For loops are most certainly not code smells on most platforms. As a few people said, the mechanics of "Where" in some languages may just be cloaking a for loop. More importantly, for loops tend to be much more performant, can be inlined easier, and generally produce less garbage than lambdas and other similar language constructs. It may different than I last looked, but back when I used to touch C#, for was most certainly preferable for anything performance sensitive provided you didn't need laziness, and if you did, there's still at least "yield" (though at that point, we're approaching what Where can does anyway). I could go on about cache lines, trashing, GC pauses, and so on, but hopefully you get the idea.

Overall, I am afraid I must disagree and point out that your advice you treasure is too generic. FOR and IF are very valuable in certain contexts. I think the real advice someone might have been trying to give you is to aim for more functional constructs, that is functions that are pure/idempotent/referentially transparent, compose, and operate on sets of data where possible rather than individual points of data. Like any advice, this isn't universal and quickly unravels in many situations such as performance-sensitive contexts like game programming, real-time programming, and so on, or may in fact just be the best practice of the target language.

optionalparens··on Ask HN: What cool development languages/tools changed your career?
I'd agree with most of this. I feel like the decision to use the JVM is what made Clojure useful at work for me vs. other languages like Elm, Elixir, Haskell, and so on that I can only just play with at home. Elm is cool but I can't justify it professionally.

People really should not discount the importance of having a big ecosystem, at least transitively in some way (ex: Clojure -> Java/Scala/Groovy). Once upon a time I took a break from C and C++ dev to do Smalltalk. It was glorious and productive, but at the same time I had to literally write everything myself. The community, even at the height was relatively small vs. some languages today. The worst was writing low-level stuff that while I could do, gave me the voice inside my saying, "WTF why am I wasting time on this." No one should ever do that if they can help it; it just eats your time.

The only real situation that comes to mind where I personally felt justified reinventing the wheel entirely was game development (ex: custom allocators, custom pipelining, entity systems). That still was time lost I could have been using to make a game and get other things done, but there were very good reasons like performance. Console development in particular was exactly this - it's not like I could go out and ask someone for their NES libraries or even in later years, PS3. Games don't generally reuse much code and certainly not when a generation of consoles is brand new with a new architecture. I could have written code like an idiot, but I chose instead to write stuff against the platform. We did well because of it vs. competitors. You can say Engines handle some of that for my specific cases, but that's discounting that huge chunks of a game are not in fact the engine or that some games preclude the use of an engine for various reasons or engines sometimes end up having the opposite effect (ex: Star Citizen).

optionalparens··on Ask HN: What cool development languages/tools changed your career?
Aware it's bad form to reply twice, but here's a separate post about what I dislike in Clojure from an honest perspective and mostly what I feel the community would agree:

* It's on the JVM (good and bad). JVM is boring, JVM loves crazy config and Java libraries. JVM has legacy baggage. JVM has garbage collection which precludes Clojure from some problem domains or otherwise handicaps it (game dev, real-time) somewhat. The list goes on.

* Core.Async is great, but parts of it can't really be optimized because of the JVM, once again. Go does a better job supporting some of the same constructs at a lower level. Counter-point: I am light years more productive in Clojure than Go because of functional programming, immutability by default, and better/more libraries for my purposes given the entire JVM ecosystem.

* Macro Debugging. Yeah, there's not much getting around this, but I mentioned some tips in my other post.

* AOT. It's there if you need it but it's less than thrilling to work with.

* Multiple versions of Clojure in the same JVM. People are working on it, but it's an issue caused by the JVM once again. Anyone who has used Storm has probably hit this at least once.

* Editors. There's Emacs and IntelliJ/Cursive, but the rest of the pack of popular editors have questionable or more limited support. Fireplace + Vim is decent too. A good example I saw recently was someone was lacking good, bug-free Clojure support thus far in VSCode. This is mostly due to community size.

* Community size. It causes a lot of things. On the plus, the community is more friendly, open, and accessible at all levels. There's no layers between people very much or hierarchy. On the negative side, there is less output because of it, though I feel sometimes this helps with quality control. Ability to use Java libs helps here.

* Null/Nil/Exceptions. I agree with how Rich gave treatment to nil, but I mention it because a lot of people hate it, especially with some ops that return nil. If you are a monad person, this will start to get to you. Exceptions also bubble up sometimes and mess with your beautiful functional compositions because of Java underpinnings.

* Functional purity. I worked in various Lisps, Haskell, and others. I don't buy this argument, but some people would rather burn themselves alive than use an impure pestilence like Clojure.

* Graphics Programming. I mean you have Java and some Clojure GPU libraries, but it's kind of weak. This applies to most languages that aren't C or C++ though.

* Certain domains. I mentioned graphics, I'll also again mention real-time and games. I don't think you should be writing the next Mars Lander in Clojure.

* Garbage. Again, JVM, but it's worth stressing that Clojure generates even more garbage than normal in some cases. You can avoid this if you really care and can shortcut some things by making use of transients.

* Performance. Transients also will help here. Clojure performance is pretty good, but it's not Rust or C good. Like any language, you need to understand where the costs accrue with productivity.

* Legacy core or widely-used libraries. Some of these suck or have some design issues. I personally don't like zipper for example and use 3rd party stuff if I want the same thing. Core.typed for awhile was bothering me too.

* Startup time. It sucks. It's getting better, but it is a hard thing to make progress on. Pixie is one alternative if you want something similar in another language, though I'd personally either stick with Clojure or pick a different language if that was important to my app. Example: not the best thing in the world for shell scripting.

* Pre-existing knowledge. It's not a requirement, but it certainly helps to have other languages under your belt first. Knowing Java and the JVM really helps, especially with debugging if you are that lost.

* Lein/Maven. It's getting better, there are alternatives (boot), and these tools are pretty awesome compared to most (looking at you Go and also Nodejs). Still, there's some rough parts here carried over from maven. For instance, "lein clean" is a thing.

* Size. Heaven help you if you want tiny output of a binary/package (ex: JAR). But then again, you're using the JVM so I assume you didn't believe in such things.

* Lack of tail optimizations. JVM issue again. Clojure works around it, but it would be nice to have had at the start. This angers Lisp purists.

* Namespace issues. Mostly just about blowing up REPL state. Namespacing is actually pretty good, it just has some limitations in the Lisp sense.

* What is broken by design to some degree will be at best patched, not fixed. Rich has stated numerous times he doesn't want to entirely break peoples code, but he will try to patch things. A good example is transducers were an improvement, patch, and built in a way that didn't break existing stuff. This means though some of the rough parts are here to stay.

There's many more, but that's my honest perspective for you. I would never pick 1 language for all projects or even most of my projects. Use the best tool for the job. Clojure sometimes is it for me, hopefully for you too. Good luck.

optionalparens··on Ask HN: What cool development languages/tools changed your career?
Wow, lots of questions. I am exhausted but will do my best to provide an initial answer.

> impossible to debug efficiently without a) understanding everything around it and b) printing everything. Debug statements seem to "ruin the cleanliness" (as well as genuinely ruining threading macro flows.

I've never once had to add a debug statement to my Clojure code, not sure what you are doing honestly. You can easily debug with Emacs + Cider which allows setting breakpoints, inspecting, and evaluating forms while debugging. This is much more than debuggers in many languages. Further, you can also use Cursive + IntelliJ which gives you pretty much the same thing, only more like most people who have done Java, C++, or C# are used to in the various associated IDEs such as IntelliJ, Eclipse, Visual Studio, (or Emacs/Vim for that matter) etc. Given the data you are dealing with most of the time is immutable, things couldn't be clear IMO.

The only time I find myself printing things is in the REPL. A few years ago I did this more often in Chrome in ClojureScript, which mostly goes away now with one or more of nREPL, Nightlight, Figwheel (or the many similar libraries). In fact I'd say the debugging situation here is better than most languages because you can instant eval things as well as live code, and see those changes immediately in the browser.

Regarding threading macros, I assume you're talking about (->, ->>, ->as, and so on). Again, you can just eval these partially in the debugger, and worst case, bind something to a value you set in the debug session as you would in a plain REPL session. I would agree these are harder to step through. If for some reason you meant macros in general, I'll repeat what I always say to new Clojure and Lisp users in general - do not write macros at the start, and when you do, question the reasons why you are doing so. Macros are insanely useful and powerful when you need them, but most of the time you do not for the average app (obviously many exceptions). Worst case, you can macro expand, paste that, and debug or debug the macro expand in an debug eval.

Overall, I've found debugging to be substantially less pleasant in most languages that are popular such as Python and Ruby vs. Clojure but less pleasant than say Smalltalk or a Lisp machine. Like many languages, the situation with Clojure improves over time. People complain about the stack traces but most of the time they don't bother me and each version has improved on that. I came from the assembler, C, Fortran, Lisp world, so in some ways that has made me more keen how to write code that is easy to debug and to not fear debugging.

> Do other companies use Clojure for non trivial web applications? Have these Clojurians ever worked on a properly complex system? A lot seem to do just data analysis with Clojure. More importantly, have they ever worked on a properly complex system that they haven't been involved with from the start where debugging comes back to 'intuition' and 'whack a mole' type debugging?

Yes, there are various lists out there if you Google some. A brief list: Amazon, Netflix, Pivotal, Walmart, Heroku, Factual, Capital One, Roomkey, Spotify, Soundcloud, the list goes on. I think it's fair to say at least one has a complex app and at least one is a not for data analysis. Clojure is quite often used at very large companies that are almost surely building systems more complex than yours (no offense, just basic probability). Saying Clojure seems to be used mostly for data analysis and therefore implying it might not be good for web apps is like saying that about Python, which in fact is used more than Clojure for data analysis.

Regarding, web applications, by nature they are trivial compared to many domains. Of course you can make things complicated by adding a lot of moving parts, but these things are usually complimentary to a web app (ex: stream processors like Spark, Storm, Google Dataflow). You can also make things more complex than they need to be by bolting on frameworks and trying to shoehorn your business and code concerns into it. This is one reason some people like lighter frameworks for some purposes and heavier for others (see Django vs. Flask for instance). Clojure generally spurns heavy frameworks for web stuff because functional programming tends to encourage or even require composition. As such, things already fit together and simply picking well-tested libraries to form your "stack" tends to let you use the right tool for the job more readily. Obviously this is somewhat subjective, but I think other people who insist on heavy frameworks have something to learn here. If their framework was so awesome, we would not need 10 more next week, and yet that is what happens.

Regarding "intuition" and "whack-a-mole" debugging, I would agree that the former is important, while the latter is a sign you've done something terribly wrong. Clojure like many functional or data-first languages tends to push you towards certain tracks that should really not lead you to whack-a-mole debugging. The idea of immutability by default and functional composition in part is that it is harder to screw up your state. This should make debugging very clear at runtime since you can quite often literally dump your entire state and have quite high visibility into what is happening in your application. A good example of this WRT web dev as you mention is ClojureScript (yes, not Clojure but same principle applies) and ReFrame or Om-Next. You have a single representation of your state as an immutable database that you update instead of things scattered about, meaning you can inspect it, query it, access it across threads (if it was on the server), etc. In Clojure and many languages, you need to think in terms of operating on data structures not classes, objects, or potential language construct distractions. This again drives away distractions while debugging that leads to shots in the dark. This of course should feed your intuition too in that if you see something with a weird state, you did something wrong like reset! instead of swap! or used mutability or you're just understanding your own code wrong.

It's not really fair to compare, but like I said, I find the debugging situation to be excellent. The fact that you can also live code with the browser, work directly in a REPL session (I open them for days), and so on means you can potentially write and test your code easily at the same time. This is somewhat like TDD, but instead of just writing a unit test, you actually run the code and get more immediate iteration and feedback. Of course you can still do test-first TDD too and eval those and even run the tests in the REPL. There are some traps here like stupid things you can do in the REPL, but there are many libraries to help you solve this that promote practices that are good regardless of the REPL (ex: Component, Mount).

I'm already writing too much, so I'll say with regard to what Rich says, just read Clojure news groups and JIRA and such. He has said many times Clojure is essentially a pragmatic balance of some of the super powers of Lisp with the practicality but limitations of the JVM. Do you want a perfect language or one that helps you get work done today but maybe better than a lot of what is out there? Moreover, do you want a language you can use in reality or just academia? Clojure solves that via the JVM and a huge existing ecosystem.

Anyway, feel free to ask more and good luck. I am sorry if I sound harsh, but I am trying to give you real answers rather than fluff.

optionalparens··on Social Media’s Dial-Up Ancestor: The Bulletin Board System
Funny enough, many BBSs were only open at night. Usually it was because someone only had one line, but also sometimes it was because a kid was hijacking the second line (presumably).

You would think such BBSs would have failed, but many were super popular in spite or even because of it. As a whole though, the bigger and better ones were multi-node and always up though.

optionalparens··on Social Media’s Dial-Up Ancestor: The Bulletin Board System
Oh wow, Major BBS. That brings back memories. I thought both Major BBS and Wildcat were garbage.

I am sure Synchronet is solid in many ways in the new version. The problem I have with a lot of software is there are big drop-offs across many of the categories I'd evaluate at least classic BBS software on.

These qualities includes but are not limited to:

* Messages - Message formats, compression, support for sync/distribution optionally, message interface

* Files - Warez boards often correlated highly with this. Things like tools for organizing files, scaling out to large numbers of files, and so on.

* Protocol Support - Does it support or can support be easily added? Ymodem, Xmodem, Zmodem, Kermit, BiModem. all are examples. Moreover, how good is the support and is it stable? Does it prevent things like Leech Zmodem? This is all less of a concern these days though obviously.

* Core Stability - Can it handle a lot of nodes, connections, users, without falling on its face? Most of the "boring" software is pretty good here, while things like the software used by the art scene or warez scene often is awful here. Even in newer stuff, a lot of software leaks resources over time or gets weird bugs when left running, which is the point of a BBS.

* Chat - Does it support multi-node chat? Can you change chat and such?

* Sysop Tools - Monitoring, paging, alerts, stats, etc.

* Add-Ons/Plug-ins - Lots of software popular in underground also was good here. Does it have an object model, programming language, scripting interface? If so, are there actually things in the wild for it? PCBoard was huge in this area, so much so it made up for many faults because of this.

* Games or other app add-ons - In the old days, supporting door games and at least a core of some games was a must. One or more of LoRD, Trade Wars, BRE, SRE were generally musts.

* Security - Does it allow adding virus scanners and such? Does it check input thoroughly? Is it or was it ever backdoored?

* OS Support - This is more something I'd judge new boards on, but in the old days choice was often determined just by what you had so it's worth mentioning. There wasn't much that was cross-platform and also good.

* UI - Can you customize the UI? Can you inject things dynamically using the API or even just simple things like MCI/Software specific codes? Can you do things like adjust key mappings? Does it support various terminal modes properly (lot of new ones fail here)?

I'll stop there, but the point is that very few if any pieces of software do well across all those. For as much as I value things like stability, so many other things used to make or break your board. Somehow we were a lot more OK with downtime then, but less forgiving if things lacked functionality. This is just my opinion of course.

optionalparens··on Social Media’s Dial-Up Ancestor: The Bulletin Board System
Agreed. A lot of BBSs both thrived and ruined themselves over having pay tiers. Sometimes it was pay for "premium" content which was usually warez, porn, etc. Then there was a period of charging for access to parts of the Internet (gateways), like email or usenet messages through your BBS.Other BBSs simply asked for donations and got quite a bit because people were passionate.

Ugh, modem incompatibility was an awful thing. The modem manufacturers often got greedy or out right lied about supporting standards correctly. It really was a case of needing to pay for quality. The worst period I remember was toward the end of the era with "Win modems" tied to windows. They'd pop these pieces of junk inside Dell, Packard Bell, eMachines, Compaq, and other consumer junk.

You're absolutely right about tiered access. I will say that torrent sites, especially private ones do have some levels of tiered access. As do some web forums in terms of moderation privileges. That's about the closest you get, but it's no where near as nuanced, draconian, or as powerful. The class-based access did have positive effects like you hint it such as discouraging lurking, creating exclusivity, encouraging uploads, discouraging bad actors. I kind of laughed at the web when years back they tried to do some version of that via game-ification and in most cases it ended badly excluding the obvious notables.

optionalparens··on Social Media’s Dial-Up Ancestor: The Bulletin Board System
Thanks for the story, lots of good memories like that too. I used to always try to call boards named things like Thieves Guild, Pirates Cove, or some sort of 31337 sounding name in the hopes of discovering some new scene or underground board. The best boards were dedicated 100% and didn't even try to fake it, but did a lot of the stuff I listed below.

Regarding boards with fake or legit parts, I used to routinely page sysops on boards I thought were underground or had hidden parts. The classic ones later on were almost always based on PCBoard and later Ami/X, but highly customized. The early ones generally just ran on whatever the best software was at the time and boasted about the hardware. They'd have all sorts of legit content typically and even legit users, but so much of it was a joke. I used to call one board that was big with HAM radio people and early Internet adopters. The most nerdy discussions you can imagine. What they didn't know is that there was a second part of the board that had a huge ROM dump, Amiga, C64, and PC warez scene.

As far as sysops go, I will also admit to spying on my users as sysop and as a co-sysop on various boards. I sometimes would break people into chat and kick them off. There were also many plug-ins that initiated fake chats and logged the results. A particular one that I'll never forget on one board I was co-sysop on featured an ANSImation (animated Ansi) by JED of ACID with some troll I think flipping you the bird as it brought up chat. Sometimes we'd post the fake chats for other users for comedy purposes.

I was nice and would help people find files, talk about fun stuff, meet in person, but I was also a dictator and would boot anyone on short notice. There were often periods of paranoia from alleged "busts," most of which probably never happened though I know for sure some did. Lots of calling people NARCs and so on.

One of the funniest things I used to see people do was upload fake files. Early on it was random binary or generated text files. Later it was things like blank audio or the same pictures renamed and zip'd. They were just so desperate for upload credit and time that they'd do this insane stuff. Checking files was really a pain. Thankfully on my boards, we were snobs about content, like on the warez boards we'd think we were so cool having 0-30 day, then it was something like 0-14, then 0 day stuff. So stupid banning and deleting people for uploading something 2 months old. Same thing happened on various FTP dumps that started to displace BBSs for file purposes later on.

Anyway, BBSs and the relationship to various underground scenes was a funny thing. On the one hand, a lot of the communities could be very exclusive and created all sorts of protections, barriers, precautions, and more. On the other hand, they'd then make it super obvious what they were up to in so many ways. Classic examples include:

- Advertising your BBS on other not-so-secret boards

- Commissioning ANSI art from a group like ACID, ICE, etc. with the name in the ANSI and often the area code too. Not uncommon to see things like +1-212-YOU-WISH Sysop: Mr Man. Awesome, now I know the name and what area code to look for the number at least, if not people who run it.

- Logon screen with ANSI depicting group affiliations. THG Eastern HQ = Genesis Distro = Legion of Doom HQ. It was hilarious because even if you didn't have access, you instantly knew you called a pirate board, cracking board, art board, whatever.

- New User Application filled with terminology from whatever scene. Again, same as the previous item.

- New User Password. As if most BBSs without anything illegal would have this.

- Users with huge ratios listed. Hmm, not many files on this BBS and yet this guy uploaded 500 megs!

- Certain BBS Software. You could be pretty sure that someone running things like Ami/X were into warez, Oblivion, Iniquity, Eternity, etc. - art, and so on. The more customized with nice ANSI too, usually the more likely it was underground. Huge tip-off the board was legit if it ran something like WWIV, Wildcat!, Celerity, and a few others we all considered hugely lame. Renegade and other Telegard or Forum hacks always made you wonder on the other hand. The old stuff on Atari ST, C64 etc was harder since there was a huge deluge of stuff and not as many ones that were 100% preferred yet.

We thought we were pretty cool in those times, but wow I look back at some of it and cringe. Good times and I was lucky enough to be involved in most underground scenes, while still getting time to interact in the legit scenes too.

optionalparens··on Ask HN: What cool development languages/tools changed your career?
Lisp - It was one of my first few languages, but really learning it damaged my view of everything else. To use a real Lisp machine, Lisp debugging/backtracing, and have code as data was such a huge win over writing ASM, C, Fortran, and the many other languages I used a lot back then. I still feel almost all other languages are catching up, while Common Lisp itself I felt got ruined by a lot of nonsense even though I still use it sometimes. So both excitement and disappointment here. This is where I really learned to use functional programming and became productive. All of my code since, even in OOP takes things I learned here like data first, preferring operations on lists/sets of data, and meta-programming. This is also where I learned that syntax really doesn't matter and people while they might have preferences, they are generally too caught up on syntax for the sake of it and not what it can do for you (ex: code is data, macros).

Smalltalk - Some of the best ideas in CS that were warped, misunderstood, or ignored. Commercialism at its finest killed this and ruined the ideas from it. The productivity in this language was huge for me and the environment was and still is a wow. The aesthetics have almost always been awful though so it really bugged me that no one ever gave a practical instead of theoretical effort to improve here. The day I saw things like Gemstone Smalltalk dumping entire running states into a bug tracker and then clicking on the issue and being thrown into the debugger was one of many incredible moments. A lot could be improved, but like Lisp, lots of imitators and few equals. In terms of impact, this really led to me truly learning OOP at a higher level and made me think about code entirely differently - as a living, breathing, environment that was somehow more real than what Lisp offered. The separations from the OS into its own world made it both incredible (I still feel like using files 1-to-1 for code is nonsense) and a pain to use (ex: integrating proper source control and existing tools because of files issue).

Clojure - Finally a practical Lisp-like experience that I don't feel like a crazy person trying to "sell" to coworkers to use on a project. Lots of things here I don't like, but even the author of the language agrees with me on most of those. I like the pragmatism, honesty, openness about what is good/sucks, and more here. It's really productive for me and I feel less in Smalltalk and Lisp land. The moment was like, "Rich Hickey, OK, this guy totally gets it."

Emacs - I hated it at first, but when the concepts started to sink in for me, it made so much sense. Licensing and politics aside, it's pretty incredible. I wish there was less crust or a way to magically rewrite it and have all the good add-ons also magically rewritten. It truly is its own OS for better or worse like Smalltalk, and can be used and abused accordingly. It just still makes so much sense to me in both Smalltalk and Emacs that I'm writing code and I can use code to do things to my editor, both in terms of add-ons and while it is running (ex: if I need a special toolbar, window setup, whatever).

Acme - It's an ugly editor, but wow it's full of great ideas. I didn't particularly enjoy the mouse chording but everything else is amazing. The relationships it had with the system using it in Plan9 just made it so powerful and full of possibilities.

Overall, my best decision to improve my work was to stop listening to the masses and just try to do my own thing, with confidence. That doesn't mean just anything, rather it means follow my instincts and balance things with a healthy dose of pragmatism and extreme skepticism. That also meant ruling out new and shiny things as well as old and awesome things like Smalltalk and Lisp on many projects. Once I learned the difference of being a contrarian vs. an educated independent thinker, I became both tormented by how terrible most software is and encouraged to think completely differently and abstractly about it all. Still trying to do some great things with that attitude, and it's more the non-technical daily life struggles that are the real challenge.

optionalparens··on Social Media’s Dial-Up Ancestor: The Bulletin Board System
I am afraid I don't have any great answers other than taking some of the ideas that made BBSs great as a whole and combining them into something entirely new. There I have a few thoughts, but then we're not really talking about BBSs.

The fact things were on a phone line helped in some ways (exclusivity, time, identifiability), but doing it all through a mobile phone or other telephony does not really capture that. For one, there would only be single node BBSs unless you got creative, so I think the mobile phone part is too literal on the concept of phones.

Secondly, while this is less popular, a lot of us including myself were not actually identifiable unless we wanted to be. This happened because you could call a BBS through an intermediary such as a PBX, and it was common to war dial to find and hack these (or use open hardware) to dial out long distance. Another way was carding (stealing credit cards) to pay for calls, which would also often answer caller ID requests with another number than your own depending on what you bought.

The anonymity was more complicated as you can see, but yes, it did help quite a bit to have some sort of reputation attached to your name. A BBS handle could carry weight across many systems, and word did spread. Some Sysops were pretty nasty to people and went out of their way with that, but I think most people accepted it and didn't do things like try to take them to court like we have today. Somehow, whether they knew who you were or not, it just was not worth it and getting other users to accept you in one form or another was important. This happened via message bases, uploads (try to be top, avoid being banned for bad uploads), new user signup, games, and more. So souring your reputation had a cost if you were an avid BBSer, and even more so if you had met people in real life.

I think anything remotely similar to BBSs in terms of success needs to do at least some of these things:

- No frills access

- Tie things together as a cohesive hole

- "Character" per system. Logging on to X should not be the same as logging on to Y, but familiar enough to still be usable.

- Distributed (run by a person/people)

- No advertising. Advertising is at the root of ruining a lot

- Cross-over between the real-world and the virtual-world. Ex: In person meetings.

- Sense of urgency

- Connections to several rabid groups of sub-culture that will drive future updates, modding, usage, etc. In the old days, this was HAM Radio operators, ANSI artists, Anarchists, Punks, Crackers, Warez kids, Phreakers, D&D players, and many other groups.

- Decent give and take type systems. Ratios, time, and chat often worked this way and sometimes were all interconnected. The more you upload, the more time you get, and the more you can chat for example.

Many more things, but I'll stop there.

optionalparens··on Social Media’s Dial-Up Ancestor: The Bulletin Board System
You reminded me, should add these to the lit section:

* 2600

* Cult of the Dead Cow

* Phrak

optionalparens··on Social Media’s Dial-Up Ancestor: The Bulletin Board System
My notes are pretty scattered.

Here's some open source BBSs I had bookmarked:

* Oblivion 2 XRM => Obv 2 remake, C++, looks OK but no killer new features really and uses Boost - https://github.com/M-griffin/Oblivion2-XRM

* Enigma 1/2 => Looks interesting and possibly the best of the bunch, but also more of the same. Good ANSI support. node js-based, so major downvotes from me here - https://github.com/NuSkooler/enigma-bbs

* x84 => Python SSH/Telnet/BBS Core => Interesting, but I didn't like the code on code review, and I think both C++ and node js are better choices. Forked a few times too, so need to see what's up - https://github.com/jquast/x84

* Synchronet => I don't know much about the modern version of this, but I hated the old one. It looks quite dated, but is updated somewhat it seem - http://www.synchro.net/

* WWIV => I wonder why this cockroach keeps living, sorry. It's written in C++ and the new version may be good, I don't know since I didn't try it. What I do know is at one point I co-sysop'd someone's WWIV board and learned how bad it really is. Truly one of the worst of the popular BBS softwares ever IMO. Perhaps a base for a derivative work though - https://github.com/wwivbbs/wwiv

Some BBSs that I am relatively, but not 100% sure there is source floating around for:

* WWIV - There are 2 sources of the old, 1 Pascal and 1 C++ . The core is not so bad for the time, it's just the implementation further up is garbage.

* Oblivion/2 - I think 2.3 or something like that. Source is pretty awful, but it looked good out of the box and had lots of add-ons from art scene especially.

* Renegade - I believe this was leaked at some point, maybe official release later? It was backdoored as well for some versions. Based on Telegard.

* Forum - Used to build lots of other software. Lookup "Forum Hacks" for a ton of other source. This includes Vision, Vision/2, Vision/X. All are insanely hackable and/or backdoored. There's also Oblivion/2, Emulex, Emulex-2, and Celerity based on this I believe, and many more.

* Telegard - Based on WWIV but with monster spaghetti of Pascal, C++, and ASM. No real reason to study this unless you want to create your own hack on it, which I don't recommend. Bunch of hacks on this as well, like Renegade.

* PCBoard - Not good source (a mess), but was the creme-de-la-creme of non-underground boards and for warez boards (customized). Supported its own Pascal-like language (PPL). I think version 15 source was leaked, or at least I somehow had it/have it (somewhere). Also very extensible compared to others.

* AmiExpress - I believe source is floating around for this. Was great on Amiga and oft-copied in art scene/pcboard setups.

Other:

* BBS Archive - Bunch of source here - http://archives.thebbs.org/ra103c.htm

* Old BBS Software List - http://software.bbsdocumentary.com/

* Mystic BBS - I ran this for a bit to mess around for a few months long ago. It was never the best of the best, but always pretty good if you want something like Obv/2 but better. It seems like it's been updated a lot since and still going. Didn't find source and license is marked as some sort of proprietary freeware. Supports SSH, telnet, etc - http://www.mysticbbs.com/

In general, there's also a lot of source floating around for C64, Amiga, Atari ST, and CP/M and it's even more nostalgic than the rest. I've seen the source of tons of BBSs and they are notoriously a mess. The most common languages you'll encounter are Pascal/Turbo Pascal, C, C++, and assembler (per platform).

I'm falling asleep, but plenty more floating around. Hopefully that is a start. A few final tips

* If you want to run door games, be careful, lots of infected binaries.

* If you are running old stuff and get a hacked version of Doorway itself to run door games or a fossil driver because your BBS needs it, these also are commonly infected. Funny enough I once wasted several days trying to get a copy of Doorway to work on a friend's board, not realizing he pirated it and it was specifically infected with the Taipan virus. This copy seems to be everywhere, so clean it and it will work or find a different copy.

* Do not run any Forum or Telegard hacks to the outside world.

* If you want to build a nice BBS that's via the Internet, start with the socket side of things and don't build on a rotten core. You can do a lot with what's available on the JVM (Java, Clojure), Go, Rust, C++, Erlang, Lisp, and any language that supports concurrency to a decent amount. Don't use PHP, Python, Ruby, etc. because you're just handicapping your BBS from the start.

* If you really want to emulate the experience, you need to get ANSI support correct, and support the full spectrum of codes, fonts, and so on. Get a handle on code pages and differences between platforms like DOS vs Amiga. Some of the links above cover this pretty well.

optionalparens··on Social Media’s Dial-Up Ancestor: The Bulletin Board System
I'm not sure I could point you to anything specific since I lived through it and never bothered to look, but there seems to be some alright stuff scattered on wikipedia. You can also learn a lot just downloading old ansi packs from http://sixteencolors.net/ and reading the news and info files in each pack.

The thing is, the history of that era is huge and has many parts. The BBS Documentary covers some of it, but IMO it has a lot of flaws and underwhelming segments given the subject matter. I personally know a few people who were in that video and I can say there's nothing inaccurate or bad about what they said, but I don't feel like Jason really "got" it that well. It's better than nothing and I appreciate it was made, but it's a bit ambitious and thus needs to gloss over things.

I'd probably look into reading about some of the following which relates some to the different parts of the BBS era:

* BBS Software w/ interesting stories - Clark Development, Wildcat, Renegade, Telegard, WWIV, Oblivion/2, Forum...

* ANSI Scene - ACID, ICE mainly, then the smaller groups like Dark, Fire, etc.

* Demo Scene - Future Crew, TRSi, etc.

* Warez Scene - Razor1911, PWA, DoD, Pentagram, TRSi, THG, Fairlight, Paradox

* Music Scene - Trackers, MODs, S3M, XM, music groups, artists (Purple Motion, Doctor Awesome, etc.), Sound cards (AdLib, Roland, Sound Blaster), MIDI

* HAM Radio WRT to BBSs

* BBSs and the Internet - Mail gateways, usenet, IRC

* Phreaking - Captain Crunch, War Dialing, Boxes (blue, red, etc.), and more...

* Cracking - Mostly overlap with warez

* Emulation - Overlap with warez a lot, but there was a pretty interesting ROM dumping scene and early NES emulation scene starting

* Alternative Lit/Anarchy/Etc - Spreading this kind of stuff was really popular and most of it is now "illegal" per many laws in western countries. Most famous is Anarchist's Cookbook, the first version.

* Early Internet and versions thereof

* IRC, Usenet, Gopher, Archie, FTP, etc. is all interesting as some of those things rose and fell during these times

* Programming Languages - C, C++, Basic, Pascal, Smalltalk, Delphi, VB for a range of where some of the industry was going or didn't go. Obviously many more.

* Platforms/OS - IBM, Tandy, Amiga, C64, Atari ST, CP/M, Unix, HP/UX, Windows, Dos, DRDos, OS/2, OS/2 Warp, BeOs (later), Novell Netware, Apple II/Mac, Sparc, SGI (Irix), Desqview (used to run multi-node BBS sometimes) and many more.

* Law Enforcement Operations - Raids (ex: Steve Jackson Games), Busts, etc.

The above list is not meant to be comprehensive, just to guide you what articles, books, videos, and such that might turn up if you search for some of these things. It's a long road.

Regarding Halt and Catch Fire, I think there are things about it that ring true, but it's not so accurate. People get things done way too fast, act too much like we do today, and the office culture feels off to me. They really don't capture some of the more innovative cultures at various big companies of the time. Not even the more crazy ones like Atari's old office, though there are clear nods to companies if you pay attention. It'd be a long post to dissect it, but the short answer is no, but it's not like I experienced all there was to experience. It feels to me more like they took a lot of real things at the time, composited them together for story purposes, put on some 80s clothes, and otherwise threw things out the window. I do enjoy the show anyway though for even daring to touch that material.

Anyway, I hope that gets you started on a long, interesting path and I could add tons of more bullets to that list.

optionalparens··on Social Media’s Dial-Up Ancestor: The Bulletin Board System
Newsgroups were a bit different I always thought than BBSs, but were still much closer in feel to various message bases. The problem even from pretty early on was spam and moderation. When you did have any ad-hoc or defacto moderation, it was usually divisive and heavy handed in a way that didn't have the same vibe as a BBS.

On a BBS, a sysop would disconnect you mid session if you were being an idiot. You'd be warned, banned for some amount of time or forever. On newsgroups, it just got much more out of control with bad actors because the scale was so much larger and the authority was so much less in terms of credibility, fear, and activity.

In defense of Reddit and HN, it's just hard to scale things up with more people and deal with the related concerns of post visibility, spam, moderation, and more. I know you're not saying this, but sometimes people point that 4chan is more like BBS messages, but it's not true because most BBSs were heavily moderated, complete with co-sysop users who would log on just to do this or moderator users with escalated privileges. If anything, BBSs were the most moderated of all, it's just that some people didn't mind if you talked about certain things or used certain language because it's their BBS and they just did what they wanted.

Regarding email-length replies, I obviously love them. I generally don't agree with short = powerful in most cases except in code sometimes. Of course short replies can be focused and have a lot of value and I certainly appreciate the people that do that well. Unfortunately, short for many people means <drop 1 sentence random mental garbage> thought and leave or <me too thought>.

Finally, regarding text, I couldn't agree more. I sometimes wish all websites just gave me a command line as a second interface. I know I can use curl and APIs for a lot of similar stuff, but yeah, no, that is not the same as hitting "f" for files or even just simpler unix commands. Lobste.rs kind of did this as a joke if you want to check it out, but it's not quite right IMO but good for fun.

optionalparens··on Social Media’s Dial-Up Ancestor: The Bulletin Board System
We had a bunch of these bastards at work and at various universities local to me. I seem to recall them all hating each other and many not conforming properly to the standards. Dial and pray.

Still sometimes find these, but more often the 9600-56k more modern ranges in random server rooms and offices, still running all kinds of things that no one understands or wants to touch. If I didn't hate consulting so much now, I thought about going into this at some point to charge breakneck prices to do archaeology for these companies. I'd feel bad though replacing or touching such beauty, not to mention they often are the backbone of many businesses so that's why they are so paranoid to go near.

optionalparens··on Social Media’s Dial-Up Ancestor: The Bulletin Board System
You can find some RIP files in some of the old ansi packs from the 90s. Acid, ICE, Dark (I think) and some others (Union?) all had RIP at least for awhile. It's been too long and I only did ANSI and ASCII art in those times, though I knew plenty of people that did RIP art.

Anyway, check http://sixteencolors.net/

optionalparens··on Social Media’s Dial-Up Ancestor: The Bulletin Board System
14.4? Slow down there, friend, we lucky people were using Hayes 300 baud modems. I still remember my glorious upgrade path:

300->2400 (now we're cooking)->4800->9600->14.4->19.2->28.8->56k

USR, Courrier, and Hayes were usually the best ones for me. I skipped 33.6 among other upgrades. The Courrier also had that extra punch if you were lucky enough to get one on the other end.

The Unix stuff was pretty pedestrian as far as programs, but on Dos, Windows, Amiga, Atari ST, C64, and some others, some cool programs for connecting. I think on Dos I remember using Terminix and Telix quite a bit, but the names mostly escape me by now.

Anyway, I guess now it's better I don't have to dial with options like *70 or use the various AT codes to get online, handshake, and stay there.

← PreviousPage 3 of 5Next →