November 28, 2018 1:56 PM

If it matters enough to be careful, it matters enough to build a system.

In Quality and Effort, Seth Godin reminds us that being careful can take us only so far toward the quality we seek. Humans make mistakes, so we need processes and systems in place to help us avoid them. Near the end of the post, he writes:

In school, we harangue kids to be more careful, and spend approximately zero time teaching them to build better systems instead. We ignore checklists and processes because we've been taught that they're beneath us.

This paragraph isolates one of the great powers we can teach our students, but also a glaring weakness in how most of us actually teach. I've been a professor for many years now, and before that I was a student for many years. I've seen a lot of students succeed and a few not do as well as they or I had hoped. Students who are methodical, patient, and disciplined in how they read, study, and program are much more likely to be in the successful group.

Rules and discipline sometimes get a bad rap these days. Creativity and passion are our catchwords. But dull, boring systems are often the keys that unlock the doors to getting things done and moving on to learn and do cooler things.

Students occasionally ask me why I slavishly follow the processes I teach them, whether it's a system as big as test-first development and refactoring or a process as simple as the technique for creating NFAs and converting them to DFAs. I tell them that I don't always trust myself but that I do trust the system: it almost always leads me to a working solution. Sure, in this moment or that I might be fine going off script, but... Good habits generate positive returns, while freewheeling it too often lets an error sneak in. (When I go off script in class, they too often get to see just that!)

We do our students a great favor when when we help them learn systems that work. Following a design recipe or something like it may be boring, but students who learn to follow it develop stronger programming skills, enjoy the success of getting projects done successfully, and graduate on to more interesting problems. As the system becomes ingrained as habit, they usually begin to appreciate it as an enabler of their success.

I agree with Godin: If it matters enough to be careful, then it matters enough to build (or learn) a system.

Posted by Eugene Wallingford | Permalink | Categories: Software Development, Teaching and Learning

November 26, 2018 2:04 PM

Self-Help from Hamming

In yesterday's post, I mentioned re-reading Richard Hamming's 1986 talk, You and Your Research. Hamming himself found it useful to manage his own behavior in order to overcome his personal faults, in service of his goal to do great work. I have faults, too, and need occasional reminders to approach my work more intentionally.

I've been at low ebb recently with my own creative work, so there is plenty of low-hanging fruit to be picked after this read. In the short term, I plan to...

  • focus my reading and programming time on material that contributes to specific research and teaching problems I'm working on. In particular, as Hamming says, "you need to keep up more to find out what the problems are than ... to find the solutions" -- then get to work actually solving problems.

  • attend seminars in other departments regularly next semester, especially in our science departments. This action works in the opposite direction as the first bullet, as it broadens my vision beyond my own work. Its benefit is in providing a cross-fertilization of ideas and giving me more chances to converse with smart people outside my area who are solving interesting problems.

I'm also our department head, an administrative role that diverts much of my attention and energy from doing computer science. Hamming doesn't dismiss "management" outright, as so many scientists do. That's heartening, because organizations need good leaders to help create the conditions in which scientists do great work. He even explains why a capable scientist might reasonably choose to become a manager: "The day your vision, what you think needs to be done, is bigger than what you can do single-handedly, then you have to move toward management."

When I became head, I had some ideas about our department that I wanted to help implement from a leadership position. Do I still such ideas that I need to drive forward? If so, then I need to focus my administrative work on those goals. If not, then I need to think about next steps.

Posted by Eugene Wallingford | Permalink | Categories: General, Managing and Leading, Personal

November 25, 2018 10:50 AM

Seek Out Idea Amplifiers, Not Sound Absorbers

Richard Hamming -- he of Hamming codes, Hamming numbers, and Hamming distance -- wasn't a big fan of brainstorming. He preferred to talk about his ideas with another capable person, because the back-and-forth was more likely to help the idea reach "critical mass". But not every capable person is a good partner for such conversations:

There is also the idea I used to call 'sound absorbers'. When you get too many sound absorbers, you give out an idea and they merely say, "Yes, yes, yes." What you want to do is get that critical mass in action; "Yes, that reminds me of so and so," or, "Have you thought about that or this?" When you talk to other people, you want to get rid of those sound absorbers who are nice people but merely say, "Oh yes," and to find those who will stimulate you right back.

What a simple bit of advice: seek out idea amplifiers, not sound absorbers. Talk with people who help you expand and refine your ideas, by making connections to other work or by pushing you to consider implications or new angles. I think that talking to the right people can boost your work in another important way, too: they will feed your motivation, helping you to maintain the energy you need to stay excited and active.

This is one of the great benefits of blogs and Twitter, used well. We have so many more opportunities than ever before to converse with the right people. Unlike Hamming, I can't walk the halls of Bell Labs, or on any regular basis walk the halls of a big research university or one of the great computing companies. But I can read the blogs written by the researchers who work there, follow them on Twitter, and participate in amplifying conversations. Blogs and Twitter are great sources of both ideas and encouragement.

(The passage quoted above comes from the question-and-answer portion of Hamming's classic 1986 talk, You and Your Research. I re-read it this morning, as I occasionally do, because it's one of those papers that causes me to be more intentional in how I approach my work. Like Hamming, "I have a lot of faults", which means that there is considerable value to be found in judicious self-management. I need periodic booster shots.)

Posted by Eugene Wallingford | Permalink | Categories: Patterns, Teaching and Learning

November 23, 2018 8:26 AM

The Peter Principle of Software Growth

This morning I read Against Software Development, which considers two tragedies of software development and a moral exhortation. One of the tragedies:

Software grows until it exceeds our capacity to understand it.

This observation reminds me of the Peter Principle from business management, which points out that people in a business are promoted until to they reach a level at which they are incompetent. Success in the hierarchy ends when people find that their skills no longer match the needs of their job.

We see something similar in software. We write a program to solve a problem. At this point, we understand the program completely so, when we see an opportunity for a new feature, we extend it. We still understand the system, so we add a bit more complexity, either implementing a new subtask or elaborating an existing feature with more detail. This process keeps happening until... we don't understand the program any more. Or, more likely, we understand it at a macro level but no longer grok all of the interconnections and dependencies among components. The result is Peter-like: the program stops growing. The root cause is not the incompetence of developers, but a fear born out complexity.

Having a system under a comprehensive set of tests can help stave off this fear. With careful attention, some time, and energy, we can use refactoring can sometimes reverse the entropy that sets in over time. But often the practicalities of organizations leave us with a big piece of software that we don't really understand, a system that can't grow or be changed to fit the evolving context in which it operates.

Many companies then find themselves in an odd situation: ossifying the organization's processes and procedures in order to stay in conformance with a piece of software its developers no long understand. Software rigidity becomes organizational rigidity.

Stay vigilant! With good development practices, perhaps you can push the point of no understanding farther into the future. But be ready for the day. It will probably arrive, sooner or later.

Posted by Eugene Wallingford | Permalink | Categories: Software Development

November 19, 2018 3:35 PM

Why Don't More CS Professors Use the Results of CS Education Research?

Over the last few days, there has been an interesting Twitter thread on the challenges of getting CS instructors to adopt the results of CS education research. Actually, it started as a thread and grew into a tree... Here's a reasonable jumping-in spot if you'd like to explore.

I imagine that it's hard to get research results into the classroom in a lot of disciplines. Research can be abstract and is usually out of context for any given school. But even when research groups implement curricula and train teachers, it can be hard to spread practices that we know work well.

The answer educators give for not adopting research results often boils down to, "It's complicated." Schools are different; students are different; the end goals are different. Indeed, the original Twitter thread spawned a student diversity conversation that picked up when the energy of the original topic waned. This tweet is a nice anchor for that conversation:

Majors vs. non-majors. Undergrads vs. high school vs. elementary school. Adult software developers vs end-user programmers vs conversational programmers. Different goals: authenticity, security, software engineering, algorithmic thinking, practice production. No one way.

All of these distinctions are real. I've seen several of them affect how we teach introductory programming at my school. And let's be honest: when we talk about research in CS education, we are often talking almost exclusively about teaching programming. How we teach intro programming can, though, have a big effect on student performance in later courses.

But even in the face of these different dimensions, I still wonder why more of us don't incorporate more research results into our teaching. I have a few ideas borne out of my years as a faculty member.

I think a big part of the effect that students have on whether faculty adopt new pedagogical approaches comes an angle not mentioned in that list: competitive pressure. Departments fear that if they adopt an unusual curriculum or an unusual first language, they will lose students. These fears manifest themselves if you propose to teach a relatively ordinary language such as Ada; they grow quickly if your approach uses an esoteric parentheses language (EPL). Parents of HS students will say, "Your competitors don't use EPL or your unusual pedagogical approach. They teach Good Old-Fashioned CS, the way it's always been, a way that's proven to get graduates jobs. Why shouldn't we send our daughters and sons to another school?"

HS students and their parents do ask questions such as these, and it takes a lot of perseverance to respond over and over. Only the most committed believers can stay the course. Unfortnately, it can take a few years for the benefits of a new approach to show up in upper division courses, let alone in the performance of graduates. New curricula rarely have that much time to succeed. If the department's faculty aren't all fully committed to an approach, then as soon as enrollments dip a bit, they join the chorus. There's a scapegoat ready at hand.

Even if we step back from the competitive disadvantage angle, we can see a similar phenomenon at play. The tweet quoted above list many different kinds of learners. These distinctions can serve as a handy reason for faculty not to change when faced with CS ed research that may only apply to one student population or one context. And resistance to change is a strong force.

Speaking as a long-time professor, I think the most powerful forces against change arise not on the student side of the equation but on the teachers'. Learning a bunch of new techniques, integrating them into a coherent curriculum, and then mastering them is hard. It takes time profs don't always have a lot of. When they do have some time, reading and applying CS ed research pulls them away from their own research or even away from the things they like to do in the classroom.

Personal confession time. This all reminds me of a conversation I had with Mike Clancy many years ago. He was part of the team that developed the idea of using case studies to teach programming. I've always admired the approach and thought the intro textbook he and Marcia Linn built around it was pretty cool. When I told Mike this, he asked, "Well then, why aren't you using them? Why aren't you writing case studies of your own?" These were great questions that took me aback. My answers sound like the excuses I've talked about in this post... My colleagues were skeptical of the approach and preferred other textbooks; convincing them to change would require a lot of work and political capital. Writing case studies is hard work, and at the time I was more excited to work on my own somewhat-related ideas. "Soon", I said. But soon never came.

I sit here still admiring case studies -- and worked examples, and Parsons problems, and the design recipe, and How to Design Programs. I've incorporated the idea of design recipes into my Programming Languages course, but I haven't fully committed to it yet. The others? They are still dreams. (I did try my first Parsons problem this semester: an assembly language program in my compilers course. I liked the result and think I'll try more next semester when I teach my students functional programming in Racket.)

Am I slow to adopt evidence-backed pedagogy? Lazy? Short on time? I don't know, but I suspect that there are many reasons. Change is hard. I do hope that I haven't done my students too much disservice in the meantime.

At one point in the Twitter conversation that launched this post, someone wrote something to the effect, "convincing researchers is easier than convincing practitioners". But that brings to mind another question: Why aren't all CS ed researchers advocating the use of worked examples? Design recipe and HTDP-style curricula? Parsons problems? Why aren't more CS ed researchers using them in their own classrooms? Maybe they are and I haven't been paying attention. If that's so, then I doubt that many other CS profs know about this widespread adoption of advances among CS ed researchers either.

Some disciplines, such as physics, seem to have developed more of a culture for incorporating education research into the classroom than computer science. Can we change that? If so, I think there is room for the CS ed research community to lead the way. But... it's complicated.

Posted by Eugene Wallingford | Permalink | Categories: Teaching and Learning

November 17, 2018 4:00 PM

Superior Ideas

In February 1943, an American friend sent physicist Freeman Dyson a copy of Kurt Gödel's "The Consistency of the Continuum Hypothesis" while he was an undergrad at Cambridge. Dyson wrote home about it to his parents:

I have been reading the immortal work (it is only sixty pages long) alternately with The Magic Mountain and find it hard to say which one is better. Mann of course writes better English (or rather the translator does); on the other hand the superiority of the ideas in Gödel just about makes up for that.

Imagine that, only five years later, Dyson would be "drinking tea with Gödel at his home in Princeton". Of course, after having taken classes with the likes of Hardy and Dirac, Dyson was well-prepared. He seems to have found himself surrounded by superior ideas much of his life and, despite his modesty, added a few himself.

I've never read The Magic Mountain, or any Mann, for that matter. I will correct that soon. However, Mann will have to wait until I finish Dyson's Maker of Patterns, in which I found this passage. It is a quite readable memoir that interleaves letters Dyson wrote to his family over the course of thirty-some years with explanatory text and historical asides. I'm glad I picked it up.

Posted by Eugene Wallingford | Permalink | Categories: General, Patterns

October 21, 2018 9:53 AM

Find the Hard Work You're Willing to Do

I like this passage from John Urschel Goes Pro, about the former NFL player who is pursuing a Ph.D. in math:

The world thinks mathematicians are people for whom math is easy. That's wrong. Sure, some kids, like Urschel, have little trouble with school math. But everyone who starts down the road to creating really new mathematics finds out what Urschel did: It's a struggle. A prickly, sometimes lonely struggle whose rewards are uncertain and a long time coming. Mathematicians are the people who love that struggle.

It's cliché to tell kids to "find their passion". That always seems to me like an awful lot of pressure to put on young adults, let alone teenagers. I meet with potential CS majors frequently, both college students and high school students. Most haven't found their passion yet, and as a result many wonder if there is something wrong with them. I do my my best to assure them that, no, there is nothing wrong with them. It's an unreasonable expectation placed on them by a world that, usually with good intentions, is trying to encourage them.

I don't think there is anything I'd rather be than a computer scientist, but I did not walk a straight path to being one. Some choices early on were easy: I like biology as a body of knowledge, but I never liked studying biology. That seemed a decent sign that maybe biology wasn't for me. (High-school me didn't understand that there might be a difference between school biology and being a biologist...) But other choices took time and a little self-awareness.

From the time I was eight years old or so, I wanted to be an architect. I read about architecture; I sent away for professional materials from the American Institute of Architects; I took courses in architectural drafting at my high school. (There was an unexpected benefit to taking those courses: I got to meet a lot of people were not part of my usual academic crowd.) Then I went off to college to study architecture... and found that, while I liked many things about the field, I didn't really like to do the grunt work that is part of the architecture student's life, and when the assigned projects got more challenging, I didn't really enjoy working on them.

But I had enjoyed working on the hard projects I'd encountered in my programing class back in high school. They were challenges I wanted to overcome. I changed my major and dove into college CS courses, which were full of hard problems -- but hard problems that I wanted to solve. I didn't mind being frustrated for an entire semester one year, working in assembly language and JCL, because I wanted to solve the puzzles.

Maybe this is what people mean when they tell us to "find our passion", but that phrase seems pretty abstract to me. Maybe instead we should encourage people to find the hard problems they like to work on. Which problems do you want to keep working on, even when they turn out to be harder than you expected? Which kinds of frustration do you enjoy, or at least are willing to endure while you figure things out? Answers to these very practical questions might help you find a place where you can build an interesting and rewarding life.

I realize that "Find your passion" makes for a more compelling motivational poster than "What hard problems do you enjoy working on?" (and even that's a lot better than "What kind of pain are you willing to endure?"), but it might give some people a more realistic way to approach finding their life's work.

Posted by Eugene Wallingford | Permalink | Categories: General, Personal, Teaching and Learning

October 05, 2018 3:39 PM

Why Patterns Failed and Why You Should Care

Beds are useful. I enjoyed my bed at the hotel last night. But you won't find a pattern called bed in A Pattern Language, and that's because we don't have a problem with beds. Beds are solved. What we have a problem with is building with beds. And that's why, if you look in A Pattern Language, you'll find there are a number of patterns that involve beds.
Now, the analogy I want to make is, basically, the design patterns in the book Design Patterns are at the same level as the building blocks in the book A Pattern Language. So Bridge, which is one of the design patterns, is the same kind of thing as column. You can call it a pattern, but it's not really a pattern that gets at the root problem we're trying to solve. And if Alexander had written a book that had a pattern called Bed and another one called Chair, I imagine that that book would have failed and not inspired all of the people that the actual book did inspire. So that, I claim, is why patterns failed.

Those two nearly-sequential paragraphs are from Patterns Failed. Why? Should We Care?, a talk Brian Marick gave at Deconstruct 2017. It's a good talk. Marick's provocative claim that, as an idea, software patterns failed is various degrees of true and false depending on how you define 'patterns' and 'failed'. It's hard to declare the idea an absolute failure, because a lot of software developers and UI designers use patterns to good effect as a part of their work every day. But I agree with Brian that software patterns failed to live up to their promise or to the goals of the programmers who worked so hard to introduce Christopher Alexander's work to the software community. I agree, too, that the software pattern community's inability to document and share patterns at the granularity that made Alexander's patterns so irresistible is a big part of why.

I was a second- or third-generation member of the patterns community, joining in after Design Patterns had been published and, like Marick, I worked mostly on the periphery. Early on I wrote patterns that related to my knowledge-based systems work. Much of my pattern-writing, though, was at the level of elementary patterns, the patterns that novice programmers learn when they are first learning to program. Even at that level, the most useful patterns often were ones that operated up one level from the building blocks that novices knew.

Consider Guarded Linear Search, from the Loop Patterns paper that Owen Astrachan and I workshopped at PLoP 1998. It helps beginners learn how to arrange a loop and an if statement in a way that achieves a goal. Students in my beginning courses often commented how patterns like this one helped them write programs because, while they understood if statements and for statements and while statements, they didn't always know what to do with them when facing a programming task. At that most elementary level, the Guarded Linear Search pattern was a pleasing -- and useful -- whole.

That said, there aren't many "solved problems" for beginners, so we often wrote patterns that dropped down to the level of building blocks simply to help novices learn basic constructs. Some of the Loop Patterns paper does that, as does Joe Bergin's Patterns for Selection. But work in the elementary patterns community would have been much more valuable, and potentially had more effect, if we had thought harder about how to find and document patterns at the level of Alexander's patterns.

Perhaps the patterns sub-community in which I've worked in which best achieved its goals was the pedagogical patterns community. These are not software patterns but rather patterns of teaching techniques. They document solutions to problems that teachers face every day. I think I'd be willing to argue that the primary source of pedagogical patterns' effectiveness is that these solutions combine more primitive building blocks (delivery techniques, feedback techniques, interaction techniques) in a way that make learning and instruction both more effective and more fun. As a result, they captured a lot of teachers' interest.

I think that Marick's diagnosis also points out the error in a common criticism of software patterns. Over the years, we often heard folks say that software patterns existed only because people used horrible languages like C++ and Java. In a more powerful language, any purported pattern would be implemented as a language primitive or could be made a primitive by writing a macro. But this misses the point of Alexander's insight. The problem in software development isn't with inheritance and message passing and loops, just as the problem in architecture isn't with beds and windows and space. It's with finding ways to arrange these building blocks in a way that's comfortable and nice and, to use Alexander's term, "life-giving". That challenge exists in all programming languages.

Finally, you probably won't be surprised to learn that I agree with Marick that we should all care that software patterns failed to live up to their promise. Making software is fun, but it's also challenging. Alexander's idea of a pattern language is one way that we might help programmers do their jobs better, enjoy their jobs more, and produce software that is both functional and habitable. The first pass was a worthy effort, and a second pass, informed by the lessons of the first, might get us closer to the goal.

Thanks to Brian for giving this talk and to the folks at Deconstruct for posting it online. Go watch it.

Posted by Eugene Wallingford | Permalink | Categories: Patterns, Software Development, Teaching and Learning

October 04, 2018 4:46 PM

Strange Loop 6: Index + This and That

the view from the Stifel Theater

For my convenience and yours, here are all of Strange Loop 2018 posts:

... and few parting thoughts of the non-technical variety:

  • All the images used in these posts are photos I took at the conference. They are licensed CC Attribution-ShareAlike 3.0 Unported.

  • On Day One, Jason Dagit kept saying H.E., for "homomorphic encryption". For a while I was confused, because my brain kept hearing A.G.

  • I left my laptop in the hotel room this year, in order to engage more with the talks and the people than with a web browser. I'm glad I did: I enjoyed the talks more. I also took fewer and more focused notes. That made blogging easier and quicker.

  • I also decided not to acquire swag as greedily as usual, and I did a pretty good job of holding back... except for this beautiful hard-bound Jane Street notebook with graphed pages:
    swag from Jane Street Capital
    "Enter the Monad." Very nice. They must be doing well.

  • I left St. Louis with a lot of plastic. The Stifel Theater, the conference's main venue, does not recycle plastic. Like many conference goers, I went through a fair number of water and soda bottles. I hate to see all that plastic go into the landfill and, having driven down, I did not have to contribute. Twice a day, I took whatever bottles I had emptied, and whatever other bottles I found lying around, back to my car and through them in the trunk. When I got home, they went straight into the recycling bin. Yet another advantage to driving over flying.

I think that's all from Strange Loop 2018. It was fun.

Posted by Eugene Wallingford | Permalink | Categories: General, Personal

October 02, 2018 4:04 PM

Strange Loop 5: Day Two

the video screen announcing Philip Wadler's talk

Friday was a long day, but a good one. The talks I saw were a bit more diverse than on Day One: a couple on language design (though even one of those covered a lot more ground than that), one on AI, one on organizations and work-life, and one on theory:

• "All the Languages Together", by Amal Ahmed, discussed a problem that occurs in multi-language systems: when code written in one language invalidates the guarantees made by code written in the other. Most languages are not designed with this sort of interoperability baked in, and their FFI escape hatches make anything possible within foreign code. As a potential solution, Ahmed offered principled escape hatches designed with specific language features in mind. The proposed technique seems like it could be a lot of work, but the research is in its early stages, so we will learn more as she and her students implement the idea.

This talk is yet another example of how so many of our challenges in software engineering are a result of programming language design. It's good to see more language designers taking issues like these seriously, but we have a long way to go.

• I really liked Ashley Williams's talk on on the evolution of async in Javascript and Rust. This kind of talk is right up my alley... Williams invoked philosophy, morality, and cognitive science as she reviewed how two different language communities incorporated asynchronous primitives into their languages. Programming languages are designed, to be sure, but they are also the result of "contingent turns of history" (a lá Foucault). Even though this turned out to be more of a talk about the Rust community than I had expected, I enjoyed every minute. Besides, how can you not like a speaker who says, "Yes, sometimes I'll dress up as a crab to teach."?

(My students should not expect a change in my wardrobe any time soon...)

• I also enjoyed "For AI, by AI", by Connor Walsh. The talk's subtitle, "Freedom & Evolution of the Algopoetic Avant-Garde", was a bit disorienting, as was its cold open, but the off-kilter structure of the talk was easy enough to discern once Walsh got going: first, a historical review of humans making computers write poetry, followed by a look at something I didn't know existed... a community of algorithmic poets — programs — that write, review, and curate poetry without human intervention. It's a new thing, of Walsh's creation, that looks pretty cool to someone who became drunk on the promise of AI many years ago.

I saw two other talks the second day:

  • the after-lunch address by Philip Wadler, "Categories for the Working Hacker", which I wrote about separately
  • Rachel Krol's Some Things May Never Get Fixed, about how organizations work and how developers can thrive despite how they work

I wish I had more to say about the last talk but, with commitments at home, the long drive beckoned. So, I departed early, sadly, hopped in my car, headed west, and joined the mass exodus that is St. Louis traffic on a Friday afternoon. After getting past the main crush, I was able to relax a bit with the rest of Zen and the Art of Motorcycle Maintenance.

Even a short day at Strange Loop is a big win. This was the tenth Strange Loop, and I think I've been to five, or at least that's what my blog seems to tell me. It is awesome to have a conference like this in Middle America. We who live here benefit from the opportunities it affords us, and maybe folks in the rest of the world get a chance to see that not all great computing ideas and technology happen on the coasts of the US.

When is Strange Loop 2019?

Posted by Eugene Wallingford | Permalink | Categories: Computing, General, Personal