Tuesday, 11 March 2014

I want off

Today is the day I lost my last remaining ounce of hope. I want it to go on record I tried with you people, I really did. I wanted this work, I wanted us to be happy, but.. we just can't. Oh and by the way, it's not me... it's you.

First, this is a thing

I found this today: literally unbelievable. It's a collection of references to The Onion articles taken as factual by the author. I just don't want to live in a world where satire has been rendered obsolete... either because people are too broken to recognise it, or because reality is too broken for people to tell the difference.

Secondly, parcel deliveries

I ordered a book to my work address, which is a company name at an industrial estate. First attempt was made to deliver on Sunday. Today, I received a text saying delivery would be attempted at some point after 5. Just after 5, I thought I would stop by reception on my way out and check if the delivery had been made. The van was parked outside and the receptionist kindly caught up with the delivery driver to ask him if he had my parcel. He stated he had one more left to deliver, for Sarah, in my office. I explained I had a text stating the delivery was due today, at which point he looked at me and said "Are you Anthony?". I confirmed that I was and he replied "Ah great, your parcel is in the van, I was going to deliver it later, so you've saved me a trip" and gave me a big grateful smile.

Thirdly, ban bossy

Ban bossy Really? I mean, seriously? All I have to do, in the opinion of Jennifer Garner, Beyonce and other such assorted ass-clowns is not call my daughter bossy in order to rear a confident, self possessed young woman brimming with self-esteem. Wow, well that's just lifted a massive burden from my shoulders, because, up until now, I'd foolishly assumed rearing a child might be a super complex task which couldn't be boiled down to a simple slogan!

I've needlessly fretted that I may have to handle each scenario based on it's own merits, with no real road map to guide me but an abiding love for my child and desire to do what was best for her in the long run (which, I'd chauvinistically thought might include teaching her when it was time to give daddy just a touch of peace and shut her noise hole). However, I now realise that it's only male children that need to be prepared for the harsh realities of life by learning to curb their natural self obsession in order to become more rounded and caring individuals in the future. Girls on the other hand, need to be encouraged towards narcissism so that one day they'll have the self confidence to stand in front of a camera and say, with a straight face, "I'm not bossy, I'm the boss". Imagine your pride as you turn to the person next to you and announce "That megalomaniac douche burger is my daughter".

Previously, I had failed to realise how powerful a word bossy is. As Anna Maria Chavez tells us "When I was growing up, I was called bossy" and we can see that she's turned out to be a complete idiot, so... case closed, lets ban the word bossy. The powerful info-graphics make the case even more air tight by claiming "Between elementary and high school, girls’
self–esteem drops 3.5 times more than boys’.", obviously with a statement that powerful, you don't need to cite the study involved, it's just a fact! The correlation between a self reflective property measured in juveniles and the use of the offensive word being self evident and thus requiring no proof.

I shall be spending all my resources on finding a way off this planet and leaving you to it.

Saturday, 1 March 2014

Considered harmful: rockstar developers

Ten years ago when I told people that I worked with computers I would often get the response "you don't look like a geek". These days no one seems to think it strange. I currently work in an office in which some of the developers talk about football and have meaningful social relationships. Being a software engineer has become somewhat cooler; as part of that "coolification" process, certain things have changed and other things, which always existed, have been named and magnified. Rockstar developers have always been a thing, but now they have a name and are often seen as desirable. Before I start to explain why I think rockstar developers are harmful, lets define one and the circumstances in which they are harmful.

Characteristics

  • Above average understanding of their language.
  • Love of esoteric knowledge.
  • Egotistical style of programming.

The first two items on the list aren't in any way negative, however, they can lead to problems if not applied responsibly with reference to the environment they are used in. It's the third characteristic that I believe leads to harmful behaviour, because the "me, me, me" can overrule common sense when it comes to the application of logic in a given environment. So there is a tendency to create overly complex solutions to simple problems as small monuments to personal vanity.

Habitat

If you are a rockstar developer as described above, working on a solo project, then go ahead, knock yourself out. It's like being a singles tennis player, there's no need to alter your style for the benefit of others. Have fun, it's your code.

If you are working in a commercial environment, being paid to do a job, then it's not your code. If you are working with a small team of like-minded rockstars, then I hope it's the nirvana it should be and once again, have fun! Unfortunately, the likelihood is that you are working as part of a team of individuals of mixed ability. This, to me, is where rockstars become harmful. It's almost always a problem related to the egotistical programming style creating problems for others. If you are part of a team, then you need to act like it and put the needs of others above your own need to show off.

Obfustication

Yea, sure, bitwise operators are interesting and using them can be a shining badge of your elite status, I mean, how else will people know you can use them unless you do? In a large team, with high code churn, it's pretty likely that someone else will have to read / understand and then modify your code. If you have code reviews, then it's a certainty. Here's an illustration with some reasons why obfustication is awesome and my rebuttals. It's not a real conversation as I wouldn't change someone's code without talking to them first.

"Hey broheim, I was checking the logs and saw you changed my code dude, what's up with that man? It's like, you took my gnarly code, babyfied it. You know your code doesn't do the same thing right?"

"Yup, it's more readable now and therefore maintainable by all members of the team, so I figured it was worth changing. I understand that your code is checking purely for -1, but that's a different discussion."

  • Original code: if (!~index) index = 0
  • New Code: index = index < 0 ? 0 : index;
  • The new code is a conditional ternary operator which is used quite widely in the codebase, if it wasn't, I'd have written:
    if (index < 0){
        index = 0;
    }

Here are the most common reasons I've heard as to why something like the original code is better. In my rebuttals my arguments are designed to be for the general case of unnecessarily complex code while still referring to the specific example.

It's not my fault everyone else is an idiot.

Although I've put this point in it's harshest possible form, this is the point I feel has the most value. Finding code you don't understand and looking it up is a very valuable way of learning. In this case though, I'd argue that it's not the right code in the right place, it's just a block of vanity code. Even though you understand that the ~ operator switches the 0's and 1's around in the binary representation of the operand, it still isn't immediately obvious that the code is checking for the case where index is equal to -1. There are enough complex things which require complex solutions, lets leave simple things as simple. It's also hopelessly naive to assume that people will understand unnecessary complexity just because they should. It's like leaving your wallet in your unlocked car because no-one should steal it.

Optimisation dude!

Ok, this is a blog post all on it's own, so we'll gloss a little here. Lets just say that there are two forms of optimisation that are important in a commercial environment.

Code Optimisation

Most important point: optimise where it hurts. Looking at the performance difference in time between our different approaches is all well and good, but we need to take into account the environment in which we are working. At the end of this code, we then append the result to the DOM. Optimising a conditional in this environment is like optimising your drive from Glasgow to London by running to the car (perf. test).


Graph showing the similarity in speed between multiple conditionals when compared with the act of accessing the DOM

Maintenance optimisation

In general it is much easier to show the cost to a company in lost man hours caused by hard to maintain code than it is to show the boost in profits caused by pre-optimised code (I'm referring here to code optimised by a developer prior to any requirement from the customer). So it's usually preferable to write maintainable code first and then optimise where it's hurting.

Complexity is better

I know this may sound strange, but I have first hand experience of a culture in which a complex solution to a problem was considered better by virtue of it being more complex. After a long discussion of the differences between two possible solutions, it was finally agreed that both solutions achieved the same goal. One group insisted that the more complex solution was better "if you are a developer", yet were unable to define a single benefit of the complex solution over the simpler one. I have also been told, as a put down, "yes, I understand your proposal, it's so simple even my grandmother could understand it". Despite how crazy this sounds, it's actually an easy trap to fall into. If something has been hard to work through, it can be difficult to accept that there is an easy solution, you want it to be difficult and require a complex solution to justify the time it took you. Again, beware of your ego.

Conclusion

Coding is interesting and those of us who do it for a living are lucky, we get paid to do fun stuff. Being good at coding is something you want to show off, but like many things it's not the flashy stuff that shows your mastery. A complex piece of work, that is simple to read and understand is the sign of great coder. The good thing about this attitude is that it scales. What you think is easy to read depends on your level of competence, to someone less experienced there may be logical tricks you've used that they have trouble following. This is where they will learn from reading your code, but without the unnecessary obfustication we've been discussing.

Saturday, 8 February 2014

Code reviews

I have been doing a lot of code reviews recently. Obviously, criticising someone else's work in a constructive manner can be a tough skill to acquire, conversely, I also used to feel quite patronising making positive comments. After a while though, I think you hit your stride and develop your own style of commenting. It quickly becomes pretty obvious that you need to have a clear idea in your own head of what you are trying to achieve with your code reviews. When you start to think about what you want to achieve, you realise how much value you can get from code reviews. Yes, they are time consuming, but consistent reviewing can really add a lot of value.

  • Checking for security vulnerabilities
  • Sense checking for possible bugs
  • Enforcing the agreed architecture of the project
  • General code quality
  • Enforcing code standards
  • Training

That's a list of what we've been trying to get out of our code reviews. Because they have to be consistent, it really helped having a clear idea of what we were looking for and what our definition of "good enough" was. In a commercial environment, it's important to make only those changes with a business case and not use code reviews as an excuse to endlessly polish. Thinking "hmmm, I wouldn't have done it like this" isn't reason enough to change someone else's work, you need to refer back to your list and see if there is an actual reason. I found this the most difficult part of learning to give code reviews. I often felt strange glossing over blocks of code I didn't feel were particularly well written because they were "good enough" while commenting on jsDoc, line spacing or naming conventions which didn't meet coding standards.

Finding your voice

Through trial and error I found that asking questions rather than making statements is a good way of introducing training into code reviews. When I spot something I don't like I often ask questions around the area. It's amazing how often forcing someone to articulate what they are trying to achieve creates a eureka moment. It suddenly becomes obvious what is wrong when you notice a series of function names don't correspond to the language you are using to define the problem.

It also took me a while to realise that I didn't have to know the answer to everything in order to be eligible to do code reviews. I know that's one of the points of peer review, but it's difficult to keep that in your head when you are reviewing. I like a conversational tone in a code review to help alleviate the idea of being judged or being confrontational. I also think that it helps make the process two way. If you tell someone to check for a valid user name, they will likely just implement what you've asked for (you, who haven't been working on the code for the last 2 weeks). However, if you ask what happens when there isn't a valid user name you get input from the person who wrote the code.

At the risk of over stressing this point, you don't have to have a brilliant solution for every comment you raise. "Hmmm, something in this just doesn't sit well with me, but I am not sure what. What do you think?". Is a perfectly acceptable comment, especially if the developer comes back with the solution you failed to think of.

Oddities

Strangely, it's much easier to criticise good code than bad. Good code is easy to read and understand which makes it much easier to think of improvements. With bad code you struggle through the logic, it's difficult to understand what it does and more importantly what it's meant to do. Finding the pivot points in which you can start to improve the code is hard work and there's so much more you have to say. This is also the time when you have to be careful how your comments come across. "I would expect a function called isValid to return a boolean, not mutate the value" is making a reasonable point, but what the developer will probably read is "You are a terrible person, that is why I hate you and your ugly code" which may not have the desired effect. In cases of really bad code, I tend to avoid the review and just help the developer re-work the code in person.

Conclusion

Spending a lot of time reading other people's code may initially seem like a cruel and unusual punishment and depending on the code it really can be. Code reviews can be super time consuming if they are on a section of the code base that you aren't familiar with. However, by the end of the review, you know the code base better and you will have levelled up your "reading other people's code" skill.

Code reviews have helped us keep the quality of the code base higher than previously. It also saves us time in bug fixing by enforcing better unit tests. We also have a level of consistency running through the projects now in terms of coding standards and architecture which is really nice. It certainly makes future development faster when developers come to work on a new project and find it fundamentally works in the same way as all of the others. I can't honestly say code reviews are a fun part of my day, but the results are too useful to ignore.

Tuesday, 28 January 2014

Banning things is awesome

I wrote recently that I don't think banning things is a cost effective way for governments to solve problems. The first reason for this is simple: supply and demand; the second reason is that it's rare that something bannable is actually the root cause of the problem; finally, banning things is a restriction of personal freedoms and those should never be given up lightly.


Supply and demand

If there is a demand for a thing, banning it has, historically, created a black market supply. Banning drugs is an awesome example of this, in 2010 it was reported that every bank note in the UK was contaminated with cocaine within weeks of issue. The cost of drug prohibition enforcement in the UK is estimated at £16 Billion. I'm not suggesting that the government wouldn't squander that cash on something equally useless if drugs were legalised, just that banning things doesn't seem to work. Here's a list of other things that have been banned at one time or another:

  • Christianity
  • Drugs
  • Alcohol
  • Guns
  • Homosexuality
  • Books
  • Furbies
  • Video games (Greece)

Now here's a list of things which (to my knowledge) have been banned effectively:

  • Time travel (China)

Solving the wrong problem

It's easy to see why some people don't like guns, drugs or Christianity, but if banning them is expensive and seemingly ineffective, why is it such a popular choice? My guess is that it's a lot easier to ban something than it is to solve the actual issue. For example, where would you rather live, in a place where everyone had guns but no-one got shot, or a place where no-one had guns, but your neighbour dreamt every night of shooting you using your own ass as a silencer? It's quite possible that solving the issue of people wanting to kill each other might give better results than simply taking away one of the more effective ways of doing it. However, that's a difficult problem to solve, it's hard enough catching murderers after they've killed someone, let along before...

It's often easier to be seen to be doing something than it is to actually do something. Like when a friend wants to tell you about their problems. You could sit, listen, perhaps make some insightful comments, help them get their heads into a better place. But that's an evening you are never getting back, plus it sets a dangerous precedent. So, you take them out and get them drunk instead, it's way more fun for you and much less work. I think it's the same with drugs, it's much easier to be seen to create jobs for drug enforcement officers and pledge someone else's money to a cause than to actually try to reduce the demand for narcotics. Especially in the instances where drugs are not taken recreationally, but as an escape from appalling social conditions.

Liberty

In addition to not working, banning things is a reduction in personal freedom. There would have to be a lot of evidence of the efficiency of such a move to warrant it in my eyes. This is true regardless of whether I want to make use of that particular freedom or not. I didn't own a gun when they were legal in the U.K. nor do I base my sexuality on the legality of homosexuality. The point is the loss of personal freedoms to a government that is doing the political equivalent of sweeping mental health issues under the rug of gun control and shoving the mess of social problems into the closet of drug prohibition.

Don't worry, I'm not going to go into the tired old chat about banning one thing being a slippery slope to a totalitarian state. It just irritates me because it's lazy and not the fun type of lazy like someone getting their food delivered from a restaurant so close I can shout my order to them. It's the evil sort of lazy that encourages stupidity by pandering to it. It's easier to ban someone from t.v. for the words they use than explain that it's the meaning behind words that matters. It's easier to ban websites than to monitor your child's internet activity. It's easier to ban jam on aeroplanes than to make them safer. It's easier to ban certain breeds of dogs than to ensure the owners aren't idiots. It's easier, it's ineffective and it makes the world just a little duller.


Sunday, 26 January 2014

Are some things too complex for sound bites?

Like most people I love a good sound bite or a witty one liner. Distilling a complex issue down to a few words is a very complex task and takes a keen mind, for me, H.L. Mencken was a master of this:

I believe in only one thing: liberty; but I do not believe in liberty enough to want to force it upon anyone.

It's short, memorable and very much to the point. For these reasons, the idea is super portable, posting something like this on twitter could see your idea entering a vast number of other people's heads and finding a resting place. There is, of course, a draw back to this, ably condensed by Mr. Mencken:

For every complex problem there is an answer that is clear, simple, and wrong.


While Mencken's pithy quotes are short, memorable and well thought through, it is only the first two factors that make them repeatable and "sticky". Therein lies the rub...


If god meant for people to talk into cellphones, he would've put our mouths on the side of our heads...

Just because something is pithy doesn't mean it has value above and beyond amusement. Sometimes, that's the point of a quote, we're dealing with those times when it's not. Fortunately, some are easy to deal with, for example if they are simply factually incorrect:

The chance that higher life forms might have emerged in this way (natural selection) is comparable with the chance that a tornado sweeping through a junk-yard might assemble a Boeing 747 from the materials therein.

No, it's not.


Others, however, require a bit more thought. I saw this little nugget of wisdom today, it's not an Mencken quote and I doubt it would convince anyone to swap sides in an argument, but it seems to have the effect of cementing together people of the same view. It's tweet provoked a very focused discussion on gun control.


We keep having shootings because there aren’t enough guns yet.


It's short and memorable - so it gets a tick for being portable. But what idea does it bring to the point? The idea that guns cause shootings? That people only want to harm other people because they have access to guns? If you put a normal, healthy individual in a room full of guns will they transform into a murderer? Or are there more complex reasons why shootings occur?


Get to the point


I chose H.L. Mencken's quotes because they are great examples of the power of short, memorable phrases; they sum up a large idea correctly without room for error in interpretation. It's pretty obvious that saying things that are just blatantly wrong is to be avoided in short, memorable phrases as in long, unmemorable ones. The reason for this post is the final example, where the phrase is ambiguous. It's hardly worth a blog post to explain that people should say what they mean and try not to be ambiguous or wrong, but this is where short, memorable phrases tend to be different. They entice us with a witty, highly repeatable phrase which supports our view on a subject. It's flattering to think that others agree with us and the tendency is to repeat these things without thinking too much about them. However, if they are not exact, if they don't focus on saying only what they mean, other ideas can slip in unnoticed.

Most people would agree that shootings are a bad thing and the fact that there are so many shootings is a form of evidence that the wrong people have the guns. The passenger idea here is that banning guns would solve the problem. I could be persuaded to agree with the comment "I don't feel comfortable with the general public having guns because they need to be told to wash their hands after using a public toilet". But I see no evidence to suggest that banning things is a reasonable way to solve the problem.

The reason Mencken wrote so many quality little quotes is that he took the time to say exactly what he meant, not sacrificing precision for brevity. When his topic was more complex, he was less brief. However, in short phrases lacking that exactness there is the danger of introducing passenger ideas, either intentionally or by accident.


The fact that I have no remedy for all the sorrows of the world is no reason for my accepting yours. It simply supports the strong probability that yours is a fake.


Sunday, 12 January 2014

Is it possible you might be responsible for your own misfortunes?

I'll start with a tale from real life that I feel illustrates my point. It does this so comically perfectly that it just has to be true (although these are not perhaps entirely accurate quotes).

I brutally and obviously cheated on my wife and now she's divorcing me. I love her completely and the fact that she won't give me another chance has ruined my life. Why is she doing this to me? I refuse to accept that this is just and right and will now devote my life to misery.

Hang on, wait... you're the wronged party in this tale? I don't want to come across as unsupportive, but you realise that you are refusing to accept the consequences of your actions here? That's not normally something that makes you the hero of the story or even a particularly likeable character.

On another memorable occasion a work colleague decided to regale me with a list of poor life choices which had lead him to become unhappy. I asked him if he thought that perhaps a large part of his woes might be due to poor decision making? For example, if he'd have chosen, at random, another member of staff to unburden himself to, he would, most likely, have received the sympathy he obviously required. I was genuinely interested in seeing what thought process had started with "I'm sad and need solace" and had ended with "Ah! There's Julie, she's really kind and compassionate, maybe I could tell her my problems... No, wait, here's Ant, I remember, one time, he told me that I would be the first person in the office he would sacrifice to save himself in the event of a zombie apocalypse, I'll tell him instead".

On an almost daily basis I seem to see incidents in which people are utterly unaware of the role of their actions in their own fate.

"I can't believe I got ANOTHER parking ticket - I got one yesterday as well, this is bullshit!"

"Were you parked in the same place as you were yesterday?"

"Yea."

"In the disabled bay next to the main doors?"

"Yea, I had a box to bring in..."

Imagine my joy to find that this isn't a new thing. That many plots of the most famous novels follow this pattern of obliviousness.

Frankenstein

So, Frankenstein is smart enough to create new life, but then abandons it into the world because it's ugly. Then makes a bargain with the monster under threat of having those he loves murdered. A bargain he subsequently breaks and is stupid enough to be woefully unprepared for what follows.

The monster itself turns out to be utterly wretched. "Oh woe is me, I am lonely! I am stronger and faster than normal people, I am almost impervious to the weather and require little sustenance, but those are small comfort to someone who is lonely and it's someone else's job to fix that for me".

Wuthering Heights

The entire plot here is driven by people failing to act in the face of brutal provocation. If Ellen Dean had been shot in the face at the start of the book and someone competent brought in to replace her, this would probably have been a very different novel. Of course, it's unfair to lay all of the blame on Nelly. If Edgar Linton hadn't taken so calmly to a man breaking into his house regularly to spend time with his wife things might have turned out differently too.

Heathcliff, of course, is responsible for his own misdeeds, but it's the inaction / acquiescence of others that allows them to be so devastating. If Edgar had taken action by confronting his wife's obvious love of another man, or by accepting that he had an enemy bent on his destruction and preparing for it he wouldn't have had to live his life in fear and seen his ward and eventually his daughter taken from him. Telling your child she's not allowed out of the garden isn't keeping her safe in the same way that having a fence between the tiger enclosure and the nursery isn't.

Solution

My point here is that's there's way too much boo hooing in the world and not enough taking responsibility. It's that lack of responsibility that leads to inaction. It's entirely possible to solve all of the problems discussed here in two monosyllabic words: "man up". We all have a responsibility to lead by example, great literature doubly so, so here are some amendments to our plot lines.

  • "So you see Dr. Frankenstein, you must make me a bride, you are completely in my power!"
  • "Not at all simple creature, did you really think I, the genius who created you from nothing, would chase you all this way unarmed? I have poisoned your tea and now I intend to shoot you like the dog you are. Then I shall return to my beloved Elizabeth and marry her in safety."

  • "But I've met 10 people in my life and none of them liked me, I am so lonely. It's not my fault I murdered people, I'm lonely."
  • "So super strength is not enough of an advantage for you, you need someone to solve your loneliness problem for you don't you? Well, here's how to solve it - GROW A PAIR! Now stop whining and sort your own problems out instead of placing them at my doorstep - my brother's dead for god's sake you thoughtless dick!"

  • "Ah, Heathcliff, I see you are in my wife's bedroom. I can't say I'm pleased about this, but I'll give you the chance to leave and never come back."
  • "You shall never force me to leave her be. There's no way you can stop me!"
  • "Wilson, shoot this man in the face and have his body dragged to the moors, then stop by the constabulary and explain how this mad man broken into my home and tried to assault me with the poker."
  • "Now, Catherine, perhaps you and I should discuss the future of our relationship."
  • "Oh and Ellen, you deceived me and brought this man into my wife's bedroom, you're fired."

Sorted.


Sunday, 18 August 2013

Reading, listening and comics

I have recently created an Audible account which I absolutely love. It turns the drive to and from work into a pleasant experience and I often use it when working out. It also means that I have rattled through more than the usual amount of books this year. Many of these books have come from reading round the League of Extraordinary Gentlemen comic book series. Yea, it's odd to think that a set of comics are interesting enough to get me to read the novels from which they draw their characters. So far I have read or am reading:

  • All the Sherlock Holmes novels - loved them.
  • Orlando (Virginia Woolf) - weird but interesting.
  • Raffles: Amateur Cracksman (E. W. Hornung) - good fun.
  • The Island of Dr. Moreau (H. G. Wells) - dark and thought provoking.
  • 20,000 Leagues Under the Sea (Jules Verne) - terribly dated.
  • Moonchild (Aleister Crowley) - good so far.
  • Gulliver's Travels (Jonathon Swift) - awesome.

I realise I am missing some of the main character's novels, but I'd already read Dracula, some of the Alan Quartermain novels, Dr Jeckyl and Mr Hyde, the Time Traveller, War of the Worlds and enough of H.P. Lovecraft to follow a lot of the subtle jokes and shifts in writing style.

In general reading, my recommendations are as follows:



The Yellow Birds - Kevin Powers

Frighteningly well written it also has a very powerful story. I was gripped from the very first sentence. I may have to re-think my top 10 :)



The Martian - Andy Weir

A story of the survival of an astronaut stranded on Mars. A well told story filled with humour and wit - a super easy read.



The Name of the Wind - Patrick Rothfuss

The first of a set of fantasy books following the life of a very gifted boy and his search for magic. It is superbly well told, the world and the characters are incredibly rich.



Solaris - Stanislaw Lem

A sci fi classic and rightly so - a very thought provoking look at how different an alien life form could be compared to the usual human-centric creatures we see in other novels.


Comics and graphic novels

I'd never really thought of comics as something I would want to read - I don't think the idea of super heroes really appeals to me. Then I discovered that a lot of comic book writers felt the same and I decided to give V for Vendetta a read. It's probably one of the best things I've read in a long time, my quotes file has grown fat on just this one graphic novel. I also discovered Alan Moore, which has been a real source of joy.

The art work in V is pretty dated, but the story is so amazing that I went to my local store and asked for a recommendation for more of Alan Moore's work. I was pointed to The League of Extraordinary Gentlemen as his master work. It's truly amazing, the story is a weaving of many works of literature into an alternate history of our world. There are so many wonderful places where the plots of two or more novels join seamlessly that you just stare at the page in wonder. The artwork by Kevin O'Neil is everything that V was missing. I genuinely haven't enjoyed reading something this much in a long long time. It also turns out that Alan Moore is a fan of H.P. Lovecraft and there are a few novels using that mythos - Neonomicon (the art work by Jacen Burrows is masterful) and Nemo Heart of Ice, which is an off shoot of the League with Kevin O'Neil, also outstanding.

So, if you have never read a graphic novel, I would heartily recommend giving them a try. Also worthy of mention are Neil Gaiman's The Sandman series and, if you want a gritty anti-hero I highly recommend The Punisher.