2
$\begingroup$

I apologize; I know this question is sort of open-ended and if I could think of a way to make it more specific, I would.

What would you consider a piece of CS so fundamental that it would be analogous to an elementary student learning his/her multiplication tables?

I think maybe looping code, maybe data types, and/or conditional statements. I'm looking for pointers to any scientific literature on this topic and any input anyone cares to share.

What are the absolute fundamentals that every developer must master regardless of paradigm (OOP, FP etc) or language?

Feel free to close this if it's too broad but if you do vote to close please suggest how I can narrow the question as well.

$\endgroup$
  • $\begingroup$ Learning multiplication tables, while still common, is redundant. We have calculators. What we need is understanding of what multiplication is, how to use a calculator, and enough mental arithmetic to calculate change when shopping and estimation.If tables are taught they should be taught much latter. $\endgroup$ – ctrl-alt-delor Jan 17 at 22:25
  • $\begingroup$ This may be of some relevance: en.wikipedia.org/wiki/Transformation_Priority_Premise $\endgroup$ – ctrl-alt-delor Jan 17 at 22:27
  • $\begingroup$ Patterns may be an analogy. Not just the GOF stuff (and not the anti-pattern singleton), but the wider sense. Which ones out of the thousands I don't know. I suspect that functional programming is the best place to start. $\endgroup$ – ctrl-alt-delor Jan 17 at 22:48
5
$\begingroup$

"Analogous" could mean different things, depending on which analogy you choose to make. To me, the key thing about learning multiplication tables is that you are memorising the answers to some simple questions which will appear as subproblems to many other things you have to do; so that you don't have to derive the answers again each time those subproblems occur. @Buffy's answer describes some of the fundamental abstract concepts which programmers certainly need a solid understanding of, but I would not count things like "sequence" and "alternation" as problems for which we apply solutions from memory; so I infer that @Buffy sees a different analogy to the one I do.

For the analogy as I see it, there are some commonly-occurring subproblems in imperative programming which we do use memorised solutions to. I would think of @Buffy's fundamental ideas as analogous to the ability to do multiplication, and the understanding of when/why to multiply; they should be learned before it makes sense to memorise the answers to multiplication questions. Likewise, understanding what sequential, conditional and iterative statements are and when/why to use them in a program should precede memorising how to apply them to solve particular problems.

To give some idea of the kind of subproblems and memorised-solutions I mean, the below list is not at all complete, but should help to illustrate by example:

  • Q: How to iterate over just some elements of a collection? A: Write a loop over the collection, and an if statement inside the loop to "filter" for just the elements you want to iterate over. The code for processing each element should go inside the if statement.
  • Q: How to find the sum of a collection of numbers? A: Initialise a variable sum = 0, and use a loop to do sum += x for each x from the collection.
  • Q: How to count the number of occurrences of something in a collection? A: Initialise a variable count = 0, and write count += 1 each time that thing is detected to have occurred.
  • Q: How to find the "best" (maximum, minimum, etc.) thing in a collection? A: Initialise a variable best to be the first thing from the collection, and write a loop over the remaining elements. Each time a new element x is observed, check if x is "better" than the current best, and if it is, update best = x.

These memorised solutions to commonly-occurring subproblems are closely related to the ideas of "roles of variables" as described by Sajaniemi and "plans" as described by Soloway & Ehrlich; I use the word "plans" to describe them. I'm not aware of any comprehensive list of them; I was able to think of some, which I've written about in Python and used for teaching undergraduate students (with limited success - perhaps we didn't spend long enough for the students to memorise the plans by repeated practice). I have written a similar document for Java which I don't have to hand immediately, but I can post it later if there is interest.

$\endgroup$
  • 3
    $\begingroup$ This is a really nice answer. I've been building such a resource myself, though I never thought about it in quite this distilled of a manner before. $\endgroup$ – Ben I. Jan 16 at 19:14
  • $\begingroup$ @BenI. I'd be very interested to see what you have, if it's intended for public consumption. $\endgroup$ – kaya3 Jan 16 at 19:37
  • 2
    $\begingroup$ I would love to see the equivalent for functional programmers :) (i know it’s map/filter, reduce, count or length/filter, etc., but what im more interested now is: are there fundamentals beneath the paradigms? Multiplication tables don’t favor one kind of math over others, excepting perhaps algebra and geometry.) $\endgroup$ – D. Ben Knoble Jan 17 at 21:07
  • 2
    $\begingroup$ Functional Programming, does not have to be a separate thing. You can do it in any language. All the modern OO languages, that I use, have filter / map / reduce. $\endgroup$ – ctrl-alt-delor Jan 17 at 22:51
  • 1
    $\begingroup$ @OnorioCatenacci Ah, that's a debate which this comment thread is too small to contain. $\endgroup$ – kaya3 Feb 7 at 21:50
3
$\begingroup$

There are three ideas that are fundamental. The first is "sequential" action. One item and then the next. The second is "alternation" one thing or another, but not both. The third is repetition. A thing repeated some number of times.

The last is a bit more complicated because of the two cases, definite repetition and indefinite (until something happens) repetition.

If you have these you have a basis. And notice I didn't say "if statements" and "loops". Those are just ways of doing things in different paradigms.

But recursion is a special case of repetition.

At the next level are values and expressions. Again, not variables, but values.

And then, the biggest idea: abstraction. We can name things. We can name values or operations or ...


I left out concurrency, even though it is pretty fundamental. But it is seldom studied by novices.


And note, of course, that the "three big ideas" are themselves abstractions over more concrete representations that might occur in various languages.


Also, in some ways the things I mention here are more fundamental to computing than the multiplication tables are to math. For example, I can't imagine a CS graduate without a firm grounding in these. But I earned a PhD in math before I learned my multiplication tables.

$\endgroup$
  • $\begingroup$ Concurrency is easy, so long as you don't have mutation. And mutation is easy to avoid. $\endgroup$ – ctrl-alt-delor Jan 17 at 22:42
  • $\begingroup$ I was surprise your first one was not Boolean logic, then conditional. From that you get all branching and looping. If you think in terms of the ALU in a processor and then add on parts of the processor such as memory and the bus it is easy to build up the fundamental concepts. $\endgroup$ – Guy Coder Jan 18 at 15:42
3
$\begingroup$

@kaya3 answer is wonderful. I view the questions listed as things that I must be able to do by rote. When I see a particular problem, I can write the skeleton of the code without thought. The pattern is so ingrained that its use is mechanical.

In the current environment we have access to all kinds of libraries for different data structures. We no longer need to be able to build them from scratch, but we still need to understand which data structure matches our needs the best and the implications in choosing that particular implementation.

Thirty years ago (longer ?) I would have said the ability to produce the basic data structures (array based, linked list - single/double/circular, trees - and how to traverse them, hash tables - handling collisions, ...) should all be rote code patterns. Now the rote knowledge is knowing which to pick, and the implications of the choice.

These are a few more that came to mind:

  • Q: How to swap the values of two variables? A: Use a temp variable

  • Q: How to find the unique elements of a collection? A: Start with an empty collection answer and add elements only when the value is not present. How do you make this efficient?

  • Q: How to implement findFirst()/findLast() and handling "not found"? A: Understand which data structure(s) might make this easy/hard and select a "not found" strategy.

  • Q: How do you do X? A: Learn to construct good Google queries and when you find something that provides useful information, and include the link in your work so you can find it again!

  • Q: I've found something that may help me do what I need to do. How do I incorporate it in my code? A: Write a small test program containing the code, test it and really understand what it does. Then merge it into your code.

$\endgroup$
  • $\begingroup$ Those are excellent suggestions for "things a developer should know by rote"! $\endgroup$ – Onorio Catenacci Feb 7 at 21:16

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.