My gripes with Codecademy

My gripes with Codecademy

Recently my girlfriend decided to try out the Javascript section of codecademy.com. Personally I was very interested in her own pitfalls. I did a lot of research under a professor at GWU regarding education in computer science and how it could be better taught.

TL;DR I have some problems with it.

  1. The validation on solutions is often wrong. Incorrect answers get marked correct, correct answers are some times incorrect.
  2. Computers aren’t magic. There is very little explanation as to why things work, just that they do, and there’s no secondary resource to find out why.
  3. Previous ideas are brought back into lessons down the road with little mention, assuming the student has mastered the material. 
  4. Some fundamental ideas, like object oriented programming and concatenation, are often avoided for long periods of time (if ever taught).

The first course in Javascript starts by just typing your name as a string into the window. Next lesson, use the .length method. It is not explained that it’s a method, or what a string is, or how you know you can use the .length method. It just moves on to using numbers. Okay, fair, I can get with that – a beginner doesn’t need to understand functions or documentation immediately. The next few steps are just messing with numbers.

Then you get to a step where you’re supposed to “confuse” the interpreter. This is where my complaints start. You’re supposed to write in a variable that was never declared, like the word eggplant, without var in front of it (to trigger a ReferenceError). I wrote 34. This is the result:

Codecademy Fail

It echos back “Well done. You have confused the computer!”, except I haven’t. 34 is a complete valid expression in Javascript. There is no error. This totally confuses a newbie who doesn’t even know what an exception is, or why it matters, or what was supposed to happen.

I solved a problem in a different lesson by using the ternary operator that produced the correct output. It explicitly forced me to use an if-else. There are many, many ways to solve problems in CS. I was disappointed to see many of the lessons didn’t let the student attempt the problem from different approaches.

The validation on many of the lessons are busted. Incorrect answers are frequently marked correct, and this only further confuses the programmer-in-training.

In a later lesson, it asks you to log the length of a string in an array. My girlfriend puts in console.log(arr.length); where arr is the array. It considered that valid – it returned a number. She never asked me why it said 1 when it should have been 5 (the length of the string itself); she just assumed it was some sort of underlying magic, since computers are as good as magic to non-developers. This leads to my second problem:

Computers are not magic, and neither is programming. Codecademy doesn’t often explain WHY something works, just that is does.

Again, I can understand if someone’s learning, they don’t need an in-depth why. They need SOME sort of “why” though; they at least need a resource to go to to answer the why’s.

A few lessons after basic array usage they popped up again, assuming you had completely mastered them in previous lessons.

Previous ideas are not given a context. If you haven’t mastered a previous lesson, you must backtrack and attempt to re-digest that knowledge.

Often the backtracking can be several lessons before, or entire modules. There’s no documentation links and rarely any reference. Some times there are examples.

Learning your first programming language can be difficult just because of syntax. Codecademy will tell you “just do this and it’ll work” but then doesn’t bring those same “just do it” examples back. That sucks.

I worked ahead of my girlfriend to see what she would be encountering in later lessons.

The object oriented introductions were painful.

They would rather have you define two variables as objects with the exact same properties than to actually understand a constructor. One of the lessons did something like…

var bob = { 
    firstName: 'Bob',
    lastName: 'Smith',
    age: 34
};
var sarah = { 
    firstName: 'Sarah',
    lastName: 'Smith',
    age: 32
};

An earlier lesson mentioned DRY yet here we are, creating multiple variables that should be the same type of object. This is so unfortunate.

To clarify, it should be closer to…

var Person = function() {
    this.firstName = "";
    this.lastName = "";
    this.age = 0;
}
var bob = new Person();
var sarah = new Person();
bob.firstName = "Bob";
sarah.firstName = "Sarah";
//... set the rest of the properties ...

While both approaches are technically valid, and the short-hand object constructor is helpful, I think it’s pretty bad example of how to use it. There’s just no focus on types, no explanations of pitfalls. Something like 34 vs “34” vs 3+4 vs “3” + “4” is only briefly glossed over.

Codecademy really misses the mark on some fundamental ideas in comp sci, and I’m not talking algorithms or regular languages.

For someone just starting, when you try to write a program like…

var userAge = prompt("How old are you?");
console.log("You'll be " + (userAge+10) + " in a decade!");

and they get back “You’ll be 2110 in a decade!” when userAge = 21they have no resources to learn why they were wrong. They’re going to throw their hands up, declare “This Is Dumb”, and forever black mark programming as something normal humans can’t do.

It was frustrating to see how it could have been done better, so I’m going to write my own Codecademy Javascript course. I don’t even like JS, but I don’t want people to be misled. Codecademy is a really excellent infrastructure for introducing programming. It takes away the steps of getting an IDE, finding a tutorial, understanding what a compiler is and so on – that lowers the bar significantly. It just needs stronger, more coherent courses with a higher quality bar.

ISDasm

Two interesting notes from current reading:

1. You can write code that runs IL commands directly if you’re current language doesn’t support a specific command.

2. ILDasm.exe and ILAsm.exe. Clearly ILAsm.exe is an intermediate language assembler, so you could write pure IL and compile it straight from there. ILDasm.exe is a lot more interesting.

Recently I ported the PHP API for theprintful.com to .NET. I’m going to use the binaries generated from that project to see what ILDasm.exe actually does.

Rather nicely, ILDasm.exe has a GUI component (go figure). We can visually inspect different different packages, their classes, as well as all of their members:

ILDAsm.exe Screenshot

ILDAsm.exe Screenshot

 

Right now I can’t see any immediate usage of ILDAsm, but it’s nice to know it’s there.

 

I did wonder if I could write an unsafe method in C# that would inject IL for me, then compile it into my project to surface otherwise unused IL behavior. Seems like it could also be an attack vector if that’s the case.

 

Day 1 with CLR via C#

Already off to a good start! I started reading the tome this morning on the train to work. I’m tracking all my personal notes through Evernote, so I may share those down the road a bit.

There are things I’m already aware that the CLR does, but they’ll be included if I read about them and I think they’re interesting. For example, I already knew that all exes/dlls get a Windows PE header (if you’re unfamiliar, check out Corkami’s PE101 – it’s crazy good), but I think it’s interesting none the less. I also found out that there’s a separate PE32+ format for 64-bit platforms.

Metadata is actually compiled into every CLR module, which I was unaware of. This means all type information is baked directly into the module itself. Suddenly the previous black magic underlying .NET Reflector with all of it’s advanced module information and assembly cross-referencing seems obvious. That metadata is also why Visual Studio’s IntelliSense feature is so good. Everything drives off of the module metadata, meaning look ups are super-fast and reflect the actual state of the assembled module.

On that note, this metadata only gets included for managed modules. By default, C++ gets compiled down to native modules, so if you’re writing C++ you lose these metadata benefits. However, you can specify an optional compile-time switch, “/clr”, which will turn said modules into managed code. Very neat.

There’s also a very handy tool called CLRVer.exe that’s included with Visual Studio. To run it, open the Visual Studio Command Prompt. It will list installed versions of the CLR. If you supply “-all” as the first parameter, it will show all programs running under the CLR along with what version they’re using. There are separate versions of the VS command prompt, one for x86 and one for x64. It will only report on assemblies running under that particular address space. It will also exclude any process running under other usernames unless ran as admin (at least that’s the behavior I observed).

Learning & Growing

In the coming weeks I’ll be specifically writing about major lessons from CLR via C# by Jeffrey Richter.

I know how the Java Virtual Machine works, but I’m still in the dark when it comes to the CLR. I actually ported NanoVM from the AVR to the Zilog ZNEO in college.

Since I’m writing a lot of C# every day (and often high-performance C#) it’s a knowledge gap that I absolutely must fill. I’m pretty excited to dig into serious content.