I have tried to convince people that ASM is reasonable as a first stage teaching language. The reputation as a nearly mystical art practiced by a few doesn't help. The thing is, instructions are simple. Getting them to do things is not hard, the difficulty comes from tasks exceeding a scale where you can think about things at their most basic level.
It quickly becomes tedious to do large programs, not really hard, just unmanagable, which is precisely it should be taught as a first language. You learn how do do simple things and you learn why programming languages are used. You teach the problem that is being solved before teaching more advanced programming concepts that solve the problem.
IMO It depends a lot on the assembly flavour.
The best ISA for learning is probably the Motorola 68000, followed by some 8-bit CPUs (6502, 6809, Z80), also probably ARM1, although I never had to deal with it. I always thought that x86 assembly is ugly (no matter if Intel or AT&T).
> It quickly becomes tedious to do large programs
IME with modern tooling, assembly coding can be surprisingly productive. For instance I wrote a VSCode extension for 8-bit home computers [1], and dog-fooded a little demo with it [2], and that felt a lot more productive than back in the day with an on-device assembler (or even typing in machine code by numbers).
[1] https://marketplace.visualstudio.com/items?itemName=floooh.v...
[2] https://floooh.github.io/kcide-sample/kc854.html?file=demo.k...
I started with Z-80 assembly, then BASIC, then 6502 assembly, then higher-level languages like C and perl, and I think the assembly gave me a useful foundation for what was going on under the hood. I'm not sure I'd even call assembly a "language" in the sense of the others. It has instructions, not statements, and there's really no syntax.
If I were teaching a general-interest programming course, I'd probably start with just a bit of BASIC to introduce a few broad concepts like variables and looping, then a little assembly to say, "And this is what's going on when you do those things," and then move up the chain. Then when they get to something like C and go to look at the assembly it produces for debugging, they'll at least be familiar with concepts like registers and branching. So not quite the order I happened to do it in, but similar.
If you have a good macro assembler, it is only a little more difficult than C. There's just more to learn up front (things like calling conventions, register usage, etc...).
I wouldn't teach it first, but after a person knows the basics in another language, seeing how it all actually works can be fun.
I was a TA for an intro to assembly language course, which means I got my office hours full of all of the students who struggled with assembly language and had to work with them one-on-one to get them over their roadblocks to pass the class.
Assembly language is not a reasonable first programming language. There's just so many things about it that make it a poor choice for programming instruction.
Chiefly, assembly lacks structure. There's no such thing as variables. There's no such thing as functions. You can fake some of this stuff with convention, but if you make mistakes--and students in intro-to-programming will make mistakes--there is nothing that's going to poke you that you did something wrong, you just get the wrong result.
I think in most CS programs, students do learn assembly early on, perhaps not as the first language, but definitely as a second language, as required by most Arch courses.
Personally way back when, I first learned BASIC, then tried to learn C, but didn't get pointers, then learned ASM, and then pointers became obvious, and went back to C. If you're going to be using C or doing anything with hardware, learning ASM IMO is very useful just to understand how the machine really works.
> Getting them to do things is not hard, the difficulty comes from tasks exceeding a scale where you can think about things at their most basic level.
Indeed - you don't actually need to work on difficult tasks to get the intellectual benefit. Once you've properly understood what a computer is, you can absorb the ideas of SICP.
Beginners should have immediate positive feedback. It's not possible with assembly language.
> I have tried to convince people that ASM is reasonable as a first stage teaching language.
Unless you're teaching people preparing for engineering hardware perhaps, I think ASM is absolutely the wrong language for this. The first reason is that programming is about problem solving, not fiddling with the details of some particular architecture, and ASM is pretty bad at clearly expressing solutions in the language of the problem domain. Instead of programming in the language of the domain, you're busy flipping bits which are an implementation detail. It is really a language for interfacing with and configuring hardware.
The more insidious result is that teaching ASM will make an idol out of hardware by reinforcing the notion that computer science or programming are about computing devices. It is not. The computing device is totally auxiliary wrt subject matter. It is utterly indispensable practically, yes, but it is not what programming is concerned with per se. It is good for an astronomer to be able to operate his telescope well, but he isn't studying telescopes. Telescope engineers do that.
This almost feels like an argument that we should teach computer science via bare metal bootstrapping.
Start out at "here's your machine code. Let's understand how x86_64 gets started" and work your way up to "now you have the automation to compile Linux and a modern compiler".
Which would certainly have stops most of the way up for things we usually include.
x86 ASM absolutely is NOT a good first language due to it being a complete mess.
assembly is a good first language if you have a simple instruction set or machine. When I saw new people learn java, easily the hardest initial bump to get over was "what the hell is public static void main(String[] args) ?" or "eclipse didn't build it for some reason"
Python is much easier to introduce someone to because there's no boilerplate and the tooling is very simple. Assembly on x86 machines is a royal PITA to set up, and you also need some kind of debugger to actively inspect the program counter and registers.
When I took Computer Organization & Architecture, they had us play around with MARIE[1] which really made assembly make sense to me. After that, I wrote an 8080 emulator and it made even MORE sense to me.
---
The biggest problem with using ASM as a first language to teach beginners is that it is extremely tedious, error prone, and sensitive to details. It is also unstructured, it uses entirely different control flow primitives than any language they will learn in the future, meaning they will not be well prepared for learning a real language that does scale to programs more complex than a few additions and calling an OS output routine.
So why teach someone a language that doesn't have if, while, (local) variables, scopes, types, nor even real function calls?
It's a very nice exercise for understanding how a computer functions, and it has a clear role in education - I'm not arguing people shouldn't learn it at all. But I think it's a terrible first language to learn.