My history as a programmer |
Often in the USENET, I see programmers asking for advice on what web pages, what books and what language they should start with to get onto the track of becomming a programmer.
If you were to listen to Bill Gates you might find this advice:
Interviewer: Is studying computer science the best way to prepare to be a
programmer?
Gates: No, the best way to prepare is to write programs, and to study great programs that other people have written. In my case, I went to the garbage cans at the Computer Science Center and I fished out listings of their operating system. |
Of course, this is just as ridiculous as it sounds. I don't think you will find many people seriously advocating this nowadays.
Relating to my own experience, I had a "toy computer" and a few reference manuals for the BASIC programming language. For me, that's all it really took. From then on, I was hooked; Computer programming has become a rather integral part of my life. The path I took can essentially be broken down into:
|
In going over the list above I can find that the only things I did that I regret, or feel have no value: learning Fortran, corporate politics, and prolog. So given the relatively little wasted effort, I feel compelled to recommend that newbies should learn along a similar path to mine. However, what is not shown in this list is that I have a strong mathematical background and that I thoroughly enjoy programming which I view as much as a creative process as a mechanical one.
However, the average industry programmer is not necessarily like me. Nor should they necessarily desire to be so. My consumption by computers is not something I've seen many other people being taken by. To many, if not most people, computer programming is not at all a creative process, and is mearly a means of getting a paycheck. In the short term anyone bright enough to pick up a University/College degree need not do much more than that to find themselves a job in the computer industry these days.
For those people I suggest you enter a University/College which can prepare you for a career in programming, but also a career in something else, should you find passion for something other than staring into a phosphor screen 9 to 5. If you've already done that, then go see your family, career councilor, therapist, whatever. You're grown up, you can figure out what kind of a job you want, can't you?
But for those who want to get into programming. I mean seriously into programming. For those that feel drawn towards computer programming, I can make some recommendations. First, this industry is a young one, moving and changing very quickly. Picking up one particular language that seems popular right now, may not make any sense in 5-10 years. Starting the way I started, I feel, is the best recommendation I can make.
BASIC -- the first language to learn |
This is a very contentious issue on the USENET, but I do strongly suggest beginners pick up the BASIC programming language first. There are many reasons why other people advocate learning other languages, but I feel that they are generally misguided. It is impossible to re-instill into a seasoned programmer, the idea that learning to program from scratch is not a trivial thing. The deeper concepts in most other languages are totally beyond what a beginner has ever experienced or could have any hope of assimilating given they have no idea what the motivation is behind it.
Concepts such as scope, data types, pointers, modularity, and dynamic memory allocation have no meaning to someone who isn't at already familliar with some fundamental programming issues. These are all, in a sense, meta programming issues which the beginner could not possibly truly appreciate when they first pick up a language. What if it turns out the potential student is unsure of themselves and needs to decide if they can or cannot hack programming? Snowing the beginner under these concepts will only serve to encourage them to give it up.
Programming is not about following rules, structure or design, that's the job of your compiler or syntax checker (like lint.) Programming is about giving instructions to your computer and making it follow them. Its about being as creative as you can possibly be with your computer. So many programmers so easily forget this as they expound on wonderful things like object oriented programming, garbage collection, portability and all sorts of other nonsense. Trying to feed this to a beginner is going to warp how they think a computer works. And knowing how a computer works is very important, far more important than how Simonyi, Stroussup, Ritchie or Kernighan think you should write code.
BASIC provides a simple syntax with some simple rules. If you can't master basic in a very short amount of time, you can be pretty sure that programming is not for you. But just because someone can't grok templates, classes, linked lists or whatever on their first outing with programming, doesn't meant they couldn't handle those concepts with proper pre-motivation. That pre-motivation can only exist if the beginner has a good idea how to program his/her computer in the first place. Teaching them C, C++, etc., turns it into a chicken and egg problem, where they might know the solution but have no idea why things are the way they are, and consequently are unable to re-apply that motivated thinking to the future problems of programming that they won't have a book to refer to about.
Basic also gives you a lot of room to play with. As shunned as it is in this industry you can actually do some nifty things in it. Another important thing is that most Basics have machine specific extensions for doing rudimentary graphics and sound. The positive feedback the people get from being able to, in some sense, have absolute control over the fundamental user interactive features of their computer (display, and audio output) is completely unseen in languages such as C, Pascal, COBOL, FORTRAN, or other candidate beginner languages. Learning graphics in those languages is considered an "advanced concept" because it takes you away from the fundamentals of those languages whose base syntax are oriented toward managing databases, spreadsheets or doing complex mathematical calculations.
Finally, as one last attempt to convince you, Basic itself has no other role than to be a programmer's first language. It is not powerful enough to be a real programmer's tool. It lets you get your feet wet, and is a reasonable balance between high level and low level programming concepts. From basic, the beginner is meant to spring board into another direction, and should be able to no matter what second language they chose.
Once a beginner is convinced to start programming in Basic, the learning process, for most, almost takes care of itself. Show someone some simple concepts of basic programming and if they have any aptitude for it at all, they should be able to run with it on their own for a reasonable amount of time. With me for example, I started in the middle ages of computing, when there weren't any instructors to teach you how to program. I had a manual, some magazines, and a little bit of a push from the local guru (as well as a very inspirational TV program called Bits and Bytes.) After that, I was on my own. But I was in bliss, because I had what I needed to tame the computer. I could make it do what I want, and it was just up to my own ingenuity to make what ever I wanted the computer do a reality.
Of course after convincing you of this, it then begs the question as to what the second language to learn should be. This is a hard question. To get yourself up to a respectable level of programming expertise, I claim that you need the minimalist concepts that are derived from assembly language as well as highly level data structures and meta programming technqiues you can learn from Pascal, C, C++ or Ada. I don't think I can whole heartly recommend learning one before the other, so I would instead rather make the suggestion that you learn assembly and C as second and third languages, though not necessarily in that order. I think the benefit of learning high level programming structures in a language like C are not worth debating as they are so self evident. But it might not be completely obvious why I consider assembly language so important. I justify my position in the next section.
Here is a tutorial to get you started.
Bad ideas that beginners should avoid |
Basic is reasonably powerful, but is a total compromise as a way of talking to your computer. As an interpretive language, it is painfully slow, and even basic compilers fall far short of the mark versus compilers for most other languages. In terms of data or even source management, it gives you almost no tools for efficient or even exhaustive manipulation. Furthermore, the dialects of BASIC on every platform are often wildly different (on the Amiga, basic has really mutated into some weird language syntax that you wont find anywhere else.) As much as I shun the structured, modular and/or object oriented programming concepts for beginners, I at the same time whole heartedly recommend that the beginner pick those ideas up as soon as they can. These abstract programming concepts will help you manage your programs and programming style that usually can be carried to whatever other languages you learn, but can't be learned in Basic.
There are a bunch of ways to make your programs go faster, or seem to go faster that, as a beginner, is more likely to deceive the way you think about program performance optimization. The stuff you learn about programming optimization initially almost invariable turns out to be wrong. This is a more advanced topic than you may initially think it is, and it is only when you've reached an intermediate to advanced level that you should attempt to learn about programming optimization. At that time I recommend my own web pages as a reference. If when looking over my optimization pages now, it seems a little perplexing or over your head, you should probably take that as an indication that you have a ways to go before considering yourself an advanced programmer.
I have even found web pages that perport to teaching you fast game programming which are so far off the mark as to be detrimental to budding programmers who read them.
There is a disease in this industry (having alot to do with the fact that beginner programmers tend to be young males with big egos) that is giving everyone with a keyboard a false sense of superiority. Programming is like that; lots of little logic puzzles, that the reasonably astute beginner can solve in their own way fairly quickly. It is a constant feedback loop that tells them they know what they are doing and are truly one with the computer.
Many programmers fall into this trap. I should know, I fell into it. My first real job in the industry was enough to cure me of that. I quickly learned that others, who might not even be as smart as I am, had all these hard won tricks and tools up their sleeve. At first, I was falling behind them, and causing all sorts of problems with my own ideas of how to program. I eventually reached a crux, and I had to make the decision to either combust under my own deceptions about how to program, or to meekly ask advice and get help from my coworkers. I eventually chose the latter, and I am now a far better programmer for it.
Those who read my other web pages may notice there seems to be a contradiction here in that I am recommending listening to your coworkers but the opposite elsewhere. That is because I am talking about two different things. You have to talk to and interact with coworkers to get into your environment and to get up to speed with how they do things. But after a while you should seek advice from broader sources such as the Intenet, to make sure your scope is not hampered by your environment.
In my book, if you believe that, you are a beginner. You can have years, or decades of experience, but if you cannot appreciate the importance of assembly language, you will always be inexperienced to me (and others; its not like I am the ultimate authority or somethng.) This issue is at least as contentious as the choice for a first language, as there are so many people who go through school without having picked up assembly language, and so it would seem that folks like me are significantly out-numbered.
A case in point is a guy named Peter Seebach. Peter Seebach is on the ANSI C committee, and knows C quite well. Although, he aparently knows some assembly language, he gave it up in favor of sticking to straight C on his UNIX box. This guy is the last person you want to take advice from. He purports that assembly with its common problems of being difficult to manage, not portable and so on is something to stay away from. At the same time, on his website demonstrates his concept of a merge sort in pure C by supplying source code. Its some of the worst god aweful C code that I have ever seen (though it is portably written). It is not commented, poorly structured and has a lot of extra baggage it does not need (it is very large for what it is doing as I recall.) After staring at it for 20 minutes, I decided it was not worth it to try and decipher it, and instead wrote my own and posted it to the net. My version, also in clean portable C, was about 16 lines, very easy to understand, and I wrote it in about the same time that I wasted just trying to understand his code. I claim the difference is experience with assembly language. As an assembly programmer, I am well versed in a minimalist programming style, which all but forces me to find efficient ways of programming things even if they are not in assembly language.
In USENET debates with him, he would commonly refer to how things are so much better writing C on his SparcStation. I think that statement tells you where he is coming from, and it isn't the real world, that's for sure. Most programmers from beginner to seasoned expert are programming for PCs. And learning PC assembly language is more than a good exercise; it is a marketable skill. There is a common misconception that assembly job are going away. In fact this is not the case. Custom assembly is still required, especially in the volatile PC market.
And you can see this problem with a lot of C-only programmers. Just take a look at some of the gnu source out there. The regular expression library, typically distributed in source form (about 100k source), is another case in point of a huge piece of garbage used to solve such a simple problem. I spent nearly an hour just trying to decipher the API without success. And again, I wrote my own version in about 400 lines of C code, which I use on a daily basis (as proof that it is not buggy.) Again my assembly motivated minimalist style was what allows me to program in this way.
So my main point is that learning assembly (and not just superficially) is beneficial, even if you don't use it on a day to day basis. It will help you even when you are writing code in other languages. Tim Bresendham points out that assembly is also essential to knowing how you computer really works. I think it is self evident, but he is correct in pointing this out as it seems far too many people either miss or play down this important point. See my High level vs. Low level article for more.
Of course it is also possible to err the other way. That is, thinking that using assembly for ever project is the best solution. The portability abstraction and ease of implementation that you get from high level languages is often more important that raw speed or size (which is the main strength of pure assembly language implementations.) The problem with people who err in this direction is that they often miss industry paradigm shifts such as object oriented programming, or worse yet, even assembly language paradigm shifts (moving to pure 32 bit, pipelined programming, from the old style of 16 bit "code size is everything" approach.)
I hear this religious war over and over, from camps from both sides on the USENET. The problem is that the folks who never completed a college/university degree don't know what education they are missing, and the people who have just done everything through school, have nothing more to offer but textbook answers.
As I mentioned above, I did a lot of self-teaching through high school, but I went to university and did all the CS courses there as well. The combination of the two is something that always seems to keep me ahead. I answer the academics with real world pragmatic answers, and I answer hackers with cleaner, better solution based on solid foundations. The third ingredient, of course, is experience, and I've been lucky there in that what I have done so far, although it has been over such a short period of time, has been a deep, insightful, learning experience. Teamwork is the biggest thing I've gotten from my experience so far (its more complicated than you might think if you don't know this yourself.)
I strongly believe that no remotely serious facet of learning is bad, irrelevant or in anyway useless when it comes to learning about computer programming. The college/university experience has the advantage that you generally learn more than just computer programming. So if you decide you don't like computer programming, or just get burned out on it, you aren't screwed. The advantage of self-teaching is that you can often learn things that way, that no amount of schooling will teach you. It also has the advantage of being more likely to leading you towards innovative solutions.
What is a Programmer? |
In case you are very new to the world of programming, just interested or intend to be one and you are not now, then here are some of the things to help you understand what it is to be a programmer:
A programmer has a certain level of understanding about how a computer works. Programmers are usually people who delve into the details about things, and have aptitude for understanding these things usually with less an all the instructions.
Rather than using nuts, bolts, wood, or a screwdriver, a programmers tools are in pure logic, an understanding of protocals, and a fair degree of proficiency with arithmetic.
When taken as a whole the instructions that make computer programs are usually part of a high level design. The low level functions of computers are, by themselves, not usable. It is how they are put together that composes a useful program.
Ordinarily program components are developed to solve some sort of technical problem. A programmers problem solving ability will often dictate their overall effectiveness.
The problem with us humans, is that even the littlest mistakes can cause all sorts of problems for computers which are essentially 100% accurate all the time. These mistakes manifest themselves in programming glitches commonly known as bugs. The big problem for programmers is that tougher bugs the inevitably crop up in anyones programming are usually not obvious about their nature, and only show up as side effects in the final results. Here the programmer must be a detective in order ferret out these problems.
This goes hand in hand with being a good problem solver. For example, when a programmer designs something with a lot of built in feedback or monitoring mechanism, this can go a long way towards their effectiveness in hunting down bugs.
This is an optional trait to being a programmer (especially if you work for Microsoft.) Often a programmer will be faced with a very difficult problem or a problem with a solution that just seems too complex. A good programmer will try to be creative, and always try to can come up with an innovative idea or approach to solving difficult problems.
Under construction (obviously)
Beginner exercises |