RE: Teaching students memory managment

Jani Hartikainen has written an excellent post in reply to my earlier post about teaching software engineering students memory management, and his post is well worth a read.  I started off writing a comment on his post as a reply but I ended up writing more than I expected as I refined my ideas.

I agree teaching a higher level language with built in memory management as a first programming language is the more humane option as far as first time students are concerned.  As learning your first programming language and all the associated concepts is hard enough without all the nasty memory related gotchas in a language like C or C++.  Although the nice thing about learning something like C or php (as Jani suggests) is that teaching object orientation can be avoided initially, as that particular concept does seem to be something that some students struggle with a lot the first time they encounter it.

However I do think a low level language that has manual memory management should be at least experienced by every programmer, as it is a fundamental concept of programming effectively.  And I believe that having minimal experience with some form of manual memory management would help most programmers write higher performance programs.  But perhaps I was being a bit over zealous recommending that everyone learns a language like C/C++ as a first language, although I think at least a short course featuring a language with manual memory management would be invaluable to all programmers.  The course would not even need to cover object orientation as you can teach that in higher level languages that are easier to manipulate than C++: the key point of the course would be to teach memory management and its implications for writing fast high quality software.

As much as I go on about knowing assembler, I admit its not something I write very often at all, however it is something that is incredibly handy to be able to read and comprehend. Even the most basic level of understanding of the instructions for loading data from or to memory and registers, branching and basic math operations would allow you to check the compiler has actually generated the assembly code you expected. This is especially useful for debugging unexpectedly slow code in compiler optimised builds.  You also don’t need to know about all the fancy vendor specific assembly instructions, as I’ve mentioned the basics are usually sufficient to be able to understand roughly what a slow piece of code is doing to then rewrite the higher level source code in a way that prompts compiler to generate faster assembly code.  Actually writing assembly code should always be the last resort and only done by experts after all other higher level refactorings are attempted, as higher level optimisation or refactoring work is usually more effective and easier to understand.  Also, assembler is not usually easily portable to other hardware platforms and most programmers find it harder to debug assembler than normal C/C++ source code.  Plus as Jani mentions it is scary to find a block of inline assembler in the C++ program you are working as it is much harder to decipher than regular source code unless it is very well documented.

This ability to check what is going on ‘under the hood’ of your language is essential for those hard to track down bugs and when optimising your application for performance, especially where the compiler has reordered the program flow or generated unexpectidally slow code. This can also be applied to high level languages as well as C/C++: checking that the IL byte code generated by your C# compiler or the Java byte code generated by the JVM is doing what you expected can be very useful in understanding your program’s execution and performance.

Explanations

I recently helped a co-worker explain a new concept to another co-worker, as they were struggling to explain it themselves even though they were experienced working with the technology they wanted to explain.  This started me thinking afterward about the art of explaining something complicated without leaning on the established jargon for that subject, as the person you’re explaining things to is unlikely to know the jargon either.

During university I worked part time as an IT technician, which I think forced me to deal with explaining things to people without technical knowledge of the concept I was explaining. At first I was surprised at how unsuccessful I was at this and that got me thinking about why. Being able to explain something complicated in a manner where someone who has no technical knowledge can understand, is I think a very important skill to have as these sort of explanations will be required often in most sorts of careers.  And often it is those who can communicate most efficiently that succeed more than those that are the most technically proficient, as what use is proficiency or ability if no one can understand you?

The key to becoming good at explanations has a few key parts in my mind:

  • Paraphrasing while learning: When learning something new, it is highly beneficial to then paraphrase the new information in your own words.  This practice has two benefits: first you will quickly find out if you understand what you’ve just read and secondly it will get you into the habit of thinking about the information using your own terms rather than just the terms in the texts (which is what you’d be doing if you simply memorised the text).
  • Limiting your explanation: If you’re anything like me you’ll want to be as helpful as possible when explaining something, as well as exercise your whole range of knowledge on the topic at hand.  This is actually the worst thing you could do, as if you think back to when you last learned something you’ll most likely realise you didn’t learn the whole subject in one sitting but by digesting it a piece at a time.  When you are explaining something you are effectively teaching, which means someone else is learning and that means you need to keep your explanation short and compact in scope to give your student a hope of remembering it.
  • Paraphrasing to verify learning: One of the best ways to check someone has understood your explanation is to ask them to paraphrase it back to you in their own words. This is not easy to do if they are not used to it so be patient; if it takes them a few attempts, they will improve with practice.