News for hackers. Stuff that matters.
Re:The software development final exam: Mathematics by delinka on Wednesday October 10, 2012 @06:57AM (#4635795)
What I'm not getting about these is the "don't cheat" bit. First, let's be clear: he's decided the 'rules' for this exam include not researching online or getting other assistance and just answering from memory. "Cheating" is "breaking the rules."

I work in the Real World, where I don't write academic data structures every day, so I don't have this stuff memorized (there's a joke in there that start "I've forgotten more than...") I use APIs to get work done. When I need to be more academic, I search online. The only place anyone's ever required to be so 'academic' about algorithms, data structures, math, etc is in academia. Step out into a job and you have an internet of active developers and useful forums are your disposal. Even if a company hired me to write an 'academic' code library, I'd do the research, write the implementation, and (after sufficient testing, profiling, etc) forget about it.

Re:The software development final exam: Mathematics by alexkus on Wednesday October 10, 2012 @08:08AM (#4635937)
The more you "know" the less you have to go look for, and when you do have to go look for stuff on the Internet (since you're not omniscient) then you'll understand more of the pages you get back as results, and understand them faster since there's less groundwork you need to cover.

An understanding big-O notation is very important if you go searching for sorting algorithms and land on a page that has an overview of sorting functions but listing bogosort as O(n!) and insertion sort as O(n^2), both relatively easy to implement, and this relatively complicated iterative[1] quick sort that's listed as O(n log n). Without other clues someone might just implement the one that looks easiest, and it works fine on their test set of 20 elements, but blows up in the future as their application/site grows and slows to a crawl sorting through millions of rows with an insertion sort.

Or, one of the most recent questions in the Mathematics part of the exam made me snigger because someone I work with was asking what bignum library was easiest to use. Rather than just answering their question (I prefer GMP myself) I asked why; they wanted to do the equivalent of log( x^300 ) and so they needed to compute x^300 first and then take the log of it; floating-point was giving slightly inaccurate answers to what was expected when they took the log of the intermediate result. It was even worse when they tried to do log( x^9125 ) - or whatever exponent is used for daily interest on a 25 year mortgage to account for leap days.

To put it another way. Without the knowledge you end up googling, and implementing, the wrong thing. You may get the right answer/outcome in the end but it may be horribly inefficient. Or, worse, an inaccurate answer/outcome; and you may not even know.

Hammering the insertion sort analogy home; you can profile and optimise an insertion sort all you like, it's still never going to approach the speed of quicksort on mid-large datasets. Huge datasets are another matter, someone stuck with "quicksort is the best" is going to struggle when faced with hundreds of millions of rows and there are things less pessimal than quicksort.

Knowledge of processor architectures, caching and how hash tables are implemented means you know not to use a hash when a simple array will suffice; but I've seen this done plenty of times.

Etc, etc, etc.

Out of the 15 questions so far there's only been two or three that the knowledge of wouldn't have helped me at some point in my development over the last 15 years. Of those that haven't applied to me I can see why they would be important to other fields and other people.

It's one of the major reasons I decided to do a full Maths degree (part-time via correspondence) to complement the Comp Sci degree I got ~15 years ago. It's not just the obvious useful stuff like calculus, group and set theory, graphs and networks, etc. Whilst I thought that the mechanics part of the Maths degree wouldn't be very useful in my job I was surprised at how useful and ubiquitous [non-]homogenous second-order linear differential equations are in modeling things that are relevant to my job (populations -> user base, hysteresis, etc).

No doubt others find huge amounts of other knowledge in other subjects that is directly applicable to IT; psychology, education, design to name but a few.

The right choice of algorithm, and implementation, in a critical part of your code could mean the difference between having 64GB of memory per server or getting by with 16GB. It could mean 100 servers to manage your 1M users, or 10 servers; the difference between 100 servers and 10 servers to manage your 1M users could mean the difference between making a profit and making a loss. These could be the differences between your idea succeeding or disappearing.

1. Another one of my common things I do at work is replacing quicksort implemented using recursion with an iterative version so that the stack doesn't keep getting blown on large datasets. I like it when people encounter this problem and find out that stacks are finitely sized and not as big as they'd hoped they would be. "But that means..." is a great thing to hear.

Re:The software development final exam: Mathematics by nadam on Wednesday October 10, 2012 @08:31AM (#4636007)
I am not an expert of this, but:

1. I think the stack usage of Quicksort is O(log(n)). Which means it is impossible to blow up the stack unless your dataset is bigger than the number of atoms in the universe (but in that case how are you keeping it in memory?)

2. For example in Java when you call Arrays.sort() this is called:

http://cr.openjdk.java.net/~alanb/6905046/webrev/src/share/c...

(It apparently uses recursion)

I know quicksort, but not on this level: these guys researched lots of different quicksort implementations and optmized the hell out of it. This implmenetation is way longer to begin with than my naive quicksort implementation would be and is called 'dual pivot quicksort', which I did not hear about until now, despite I know how the traditional quicksort works.

Re:The software development final exam: Mathematics by gjm11 on Wednesday October 10, 2012 @08:41AM (#4636046)
1. It's average-case versus worst-case again. If you implement quicksort recursively in the obvious way, then when you get unlucky it takes order-n stack space as well as order-n^2 time.

2. Yup, it recurses, and it looks to me as if it's vulnerable to blowing out the stack in the worst cases. However, it's quite a sophisticated implementation and in practice you're probably only going to see the worst cases if you feed it actively malicious input (see, e.g., http://www.cs.dartmouth.edu/~doug/mdmspe.pdf for a paper about doing this).

[EDITED to add: (1) A little discussion of that paper on HN is at http://news.ycombinator.com/item?id=1723305. (2) I don't know whether McIlroy's "killer adversary" would actually work against this dual-pivot algorithm without some modification; it depends on how well its heuristic for telling when the pivot is being found works against this algorithm. I'd guess that it does work.]

Re:The software development final exam: Mathematics by nadam on Wednesday October 10, 2012 @08:54AM (#4636076)
You and barkell are right: I forgot the case of actively malicious input. (other than that worst case cannot practically happen, at least I think, taking a glance on this algorithm's pivot selection.)

This could be solved with randomization though. (Onlyy a few lines of code needs to be changed.)

Re:The software development final exam: Mathematics by gjm11 on Wednesday October 10, 2012 @10:01AM (#4636341)
Actually, McIlroy's "killer adversary" will work just fine against typical randomized quicksort implementations! (It effectively constructs the data on the fly, guessing when the sorter is trying to find a pivot.)

In that earlier HN discussion there was an extended (and frankly rather fruitless) debate between me and another poster about whether McIlroy's adversary can rightly be said to break randomized quicksort; that was basically terminological, and what is not in question is that if you take a typical randomized-quicksort implementation and feed it McIlroy's evil comparator, you will get order-n^2 performance.

Re:The software development final exam: Mathematics by barrkel on Wednesday October 10, 2012 @08:37AM (#4636028)
Worst case is O(n). Think about it; recursing on one half after finding a pivot which turns out to be the smallest or largest (presuming you recurse on both halves).

A malicious attacker may even craft data that causes this behaviour, if they know the library / variant being used.

Re:The software development final exam: Mathematics by alexkus on Wednesday October 10, 2012 @08:57AM (#4636089)
This is my point, the worst case of stack usage of the basic quick sort algorithm is O(n), not O(log n); O(log n) is the average case.

Consider a quicksort algorithm that takes the first element in each partition and uses that as the pivot.

When given sorted data it will iterate as:

Notation: (left set) _pivot_ (right set)

Input: 1 2 3 4 5

    () _1_ (2 3 4 5)   1 is chosen as pivot, all elements in right set
    1 () _2_ (3 4 5)   2 is chosen as pivot...
    1 2 () _3_ (4 5)
    1 2 3 () _4_ (5)
Note that for each recursion we're construction the input with the aim of leaving one of the partitions empty, so that we only ever sort 1 element (the pivot) each iteration.

So that's n-1 levels of recursion with n elements -> O(n)

Even if you take the 'middle' (left-middle if even number) element as the pivot it's possible to construct a patalogical case:-

Input: 4 2 1 3 5

    () _1_ (4 2 3 5)    2 is next pivot for right partition
    1 () _2_ (4 3 5)    3 is next pivot for right partition
    1 2 () _3_ (4 5)    4 is next pivot as left of middle for even number of elements
    1 2 3 () _4_ (5)    ...
Again, n-1 levels of recursion with n elements -> O(n)

On the other point; I'm not saying that every implementation of quicksort out there is susceptible. I'm saying that there are quite a few implementations that are in common use that are just the basic quick sort algorithm and can be made to blow through available finite stack space given large enough datasets or even semi-pathalogical input cases.

The majority of problems can be done away with by choosing a random pivot point from the set, that way it's very unlikely (but not impossible) to achieve a pathalogical case. However, such an implementation becomes indeterministic in that there's a very small but non-zero chance that the random pivots chosen will select items from the array in relative order and lead to too many levels of recursion. To me something that blows up only very rarely, and virtually impossible to replicate, is a nightmare to debug and fix. I'd much rather put the right algorithm in there to begin with to avoid this possibility completely.

There are plenty of other tricks you can implement to avoid cases like this, e.g. checking that the pivot creates partitions with at least 10% of elements in; that greatly reduces the number of possible recursions

But you'd be surprised at the number of sort implementations out there in the real world which are just implementations of the basic quicksort algorithm.

Re:The software development final exam: Mathematics by nadam on Wednesday October 10, 2012 @09:03AM (#4636107)
Thanks for your detaild answer.
Re:The software development final exam: Mathematics by irahul on Wednesday October 10, 2012 @08:16AM (#4635965)
> Another one of my common things I do at work is replacing quicksort implemented using recursion with an iterative version so that the stack doesn't keep getting blown on large datasets.

What language do you use which doesn't already have an optimized version of quicksort or equivalent?

Re:The software development final exam: Mathematics by alexkus on Wednesday October 10, 2012 @09:00AM (#4636099)
The usual suspects are recursive qsort() implementations inside libc on Solaris, HP-UX and AIX. They've got a lot better in the latest releases but our software is supported on the older platforms (as far back as Solaris 7 for example) so it has to be made to work on them. glibc has done it properly for years. So this is mainly software written in C/C++.

Other languages do sorting in one of several ways:-

1) Just wrapper libc's qsort() and so suffer the same problem if that's susceptible.

2) Implement the naive recursive stack-gobbling quicksort in their own language as a module/package/import/library.

3) Implement their own sorting algorithm that avoids lots of recursive calls or does the tricks to pick suitable pivots, etc.

It's #1 and #2 that tend to suffer from problems when sorting large datasets, or the pathalogical cases that pinpoint the absolute worst in the design of the algorithm.

Re:The software development final exam: Mathematics by irahul on Wednesday October 10, 2012 @09:22AM (#4636176)
> The usual suspects are recursive qsort() implementations inside libc on Solaris, HP-UX and AIX.

Oh, I am mainly familiar with GNU C library. Wasn't aware others were shipping recursive qsort implementation, especially considering that a non recursive qsort is an undergrad level exercise.

Re:The software development final exam: Mathematics by cperciva on Wednesday October 10, 2012 @07:02AM (#4635806)
What I'm not getting about these is the "don't cheat" bit

If I said "go ahead and use google, wikipedia, textbooks, and talk to your friends", I would have needed to make the questions harder and lengthier to compensate. I thought asking people to spend 15 minutes telling me what they know would be more feasible than asking people to spent 15 hours showing me what they can find out.

Re:The software development final exam: Mathematics by scott_s on Wednesday October 10, 2012 @12:09PM (#4636930)
Which is reasonable, since it's your time. But consider that I have three degrees in CS (BS, MS and PhD). I am employed doing CS research, primarily in systems and high performance computing. And for at least one question on each subject, I would not feel comfortable answering unless I referred to some reference. (Yes, even the architecture and systems questions, despite that being my "expertise": I can recall very little about coherence algorithms.)

The primary value of a formal education is, I think, not that you know a lot of stuff. Rather, it's knowing what you don't know. Knowing just enough to recognize "Oh, this is related to that other thing, I should go and read about that." I'm constantly doing that, as are the people I work with.

Re:The software development final exam: Mathematics by delinka on Wednesday October 10, 2012 @07:15AM (#4635833)
I understand. To gather data, you need manageable data. What will this data show you? What are you hoping to learn from this experiment? Perhaps I'm being a little cynical, but it seems to me that this information will tell you little about the craft outside of academia.

P.S. I've refrained from answering the exam precisely because I'd have to refresh my memory from online resources.

Re:The software development final exam: Mathematics by tzs on Wednesday October 10, 2012 @07:38AM (#4635882)
If you have to go to the net for basic things, you are going to be less productive than someone who is able to understand and use those things from memory, because of (1) the time it takes to find the information online, and (2) the interruption in flow.

The majority of his problems were things that I'd say are in the "should be in memory" category for those who work in the general area that the particular question covers.

Re:The software development final exam: Mathematics by delinka on Wednesday October 10, 2012 @08:16AM (#4635964)
"Why should a message be "padded" (and not just with zeroes) before being encrypted or signed using RSA?" I just happen to know this one. I know effective developers that don't. This is not 'basic' information.

"What is the expected run-time of quicksort? What is the worst-case run-time?" Who cares? Call the sort method on your array class, call a sort function. Done. I don't need to know this for everyday things.

"Name and describe the four states in MESI cache coherence." This is 'basic' knowledge? Maybe if I wrote a kernel in school, and if I did, I certainly don't remember the details of dealing with cache coherence 25 years later. I'm not a kernel developer now. Nor are a Very Large Percentage of developers in the real world.

"Which of the following two functions is faster, and why? Assume that the C code is translated into machine code in the obvious manner, without optimization." Again, I just happen to know this one. But the "without optimization" almost makes the exercise silly. As your employer, I'd want to know you have the analytical skills to find the bottleneck in the code or to discover the compiler bug whose optimization is causing problems.

"Explain the difference between a mutex and a read-write lock." Sorry, I'm using a higher-level construct. GCD from Apple, go routines in go ... do I 'fail' this question because I don't have to remember this from 15 years back?

Re:The software development final exam: Mathematics by jules on Wednesday October 10, 2012 @07:54AM (#4635910)
More importantly, you don't know what you don't know. If you don't have something in memory, even though that knowledge is readily available on the web, you probably won't notice an opportunity to apply that knowledge. That said, while I can answer these questions, they are pretty specialized knowledge. It's is a common phenomenon to think that the specialized area you work in is a big part of the world because you spend so much time in it. People should not feel bad about not knowing the answers to these questions. A web developer doesn't need to know any of these things, and he would be able to come up with web development questions that would be equally hard to answer if don't happen to be in that area (e.g. In which browsers is css-property-foo supported? or: what is faster, setting innerHTML or inserting a new elment into the DOM?). Even within the area of computer science, the author is asking specialized questions about hardware, security and algorithms. If it was about machine learning, type systems, and parsing you'd have a completely different set of questions. Or it could have been about computer graphics, compiler optimization, human computer interaction, and programming languages.