Design sense, belatedly triggering

There’s something pretty sucky about the way I’ve been structuring tinypapers. It’s getting too spaghettti-code-like. A line I wrote a few days ago to solve a problem made me feel uneasy (I think I mentioned this already somewhere?) and I couldn’t find a different approach. Then there are these more recent issues that have been making me twitchy. My design sense finally put two and two together… there’s some funky stuff going on I need to fix.

Anyway, I’m going to have to spend a day or two refactoring (and, where possible, minimizing) the “power” structure before it gets any more complicated. I just sat down with an actual pen and paper (magical tools) and it’s pretty obvious that something isn’t right. Hopefully the visual aid will help kick me into solving what’s wrong.

—–

(several hours later)

Kivy is really confusing about this, though. Because child structures and inheritance are mostly defined in KVlang rather than Python, ordinary design patterns don’t… quite work. I’m in a better position to figure this out now than before I wrote any code, of course.

Here’s the structure.

I’ve got one class (widget if you’re speaking KVlang) which controls which of the other classes is being displayed. I’m calling it a window manager. Of course, in each of the “child” classes (which don’t actually inherit anything from the window manager), there’s at least one button that’s supposed to trigger the window manager and make it display a different page.

You can’t just randomly call them from other classes. The page-switcher methods need an instance of the window manager to work. And I can’t just put the page-switcher methods in the child classes. The reason the window manager exists is that it’s the only part of the program that knows how to do that sort of thing.

So, there isn’t… really a hierarchy in the Python file. It’s mostly just there to define any logical back-end that the KVlang file might need.

The KVlang file has hierarchy all over the place. It basically declares everything.

Anyway, I’ve got this window manager. Underneath it I have the main page that lists categories of documents (“Business Cards”, etc) and each of those categories has (will have; I’m only working with one right now) its own instance of IndexPage to display the documents in that category. Each category also has an Add page for new entries.

It’s not that complicated! It shouldn’t be this complicated! It’s still complicated!

—–

(an hour later)

As you can tell, I’m still getting my head around Kivy.

Basically, whenever you need to do stuff that crosses over different classes, you have to make your method calls in Kivy. Kivy keeps basically all the class instances in memory. This gets kinda tricky if you lose track of things though.

I do need to clean up the Kivy inheritance… and then stop bashing my head against trying to make things happen in the Python file that just can’t happen in the Python file. Sigh.

Advertisements

Working Around the Decorator Pattern

…Which still seems kind of ugly to me. Less so than before now that I’ve thought about it. But I’ve also had the problem of making a better design in my mental background space for a few days. I’m not entirely sure precisely what my growing sense of program design takes offense to about the pattern–although I have a general idea and a few guesses–or where it’s going with how to fix the issue.

Note: If you’re not familiar with program patterns, this will probably be an incomprehensible blog post. My own understanding of this topic is almost nonexistent, so I can’t explain what I’m talking about, and you wouldn’t want to learn from me anyway. I’m writing mainly for my own mental clarity, and to flesh out the ideas that have been nagging me.

The only hint of a solution I’ve posed on here is that I would use more of a Strategy-shaped pattern.

Issues with Decorator that I can point out: It’s big and clunky. You can’t see everything that’s going on with your objects, and you can’t rely on being able to test for all their characteristics if you need to–which means that if a future feature needed to go back and see that information, you’d have to restructure the whole program or implement a klugey hack that would be even messier. So it’s brittle.

Probably for simple stuff it’s fine, and even in special “big” cases, but… I had a similar reaction to reading about it as when my Intro to Programming Logic class taught us about bubble sort algorithms. Roughly: “Ick.”

In the book’s example, you’re using decorators to customize coffee orders with different toppings: mocha, whipped cream, soy, steamed milk, whatever. I’ve been thinking about how you could use implementations in this scenario, or maybe put in special dedicated methods to add toppings.

Personally, I would use arrays for–

Aw, man… am I venturing into LISP territory, using arrays for stuff that probably doesn’t need arrays?

Whatever.

My first impulse is to give each individual drink object a toppingList array to work with (perhaps inherited from a superclass), and let it call different methods which would append toppings to toppingList, which could be evaluated later–for the purposes of charging extra for each topping and so on.

But I don’t like that idea much either.

Using arrays is a good start, but there has to be a way to use an interface or an abstract superclass to standardize things.

All the drinks have toppings (or lack thereof). Even if there’s another drink which would be awful combined with certain toppings, it won’t hurt to have the potential for toppings in general to exist, even if there aren’t any appealing ones right now.

Like I said, Strategy pattern would be a good one to take a hint from. You could implement an interface for toppings, and then methods for each topping that add the topping to the drink’s toppingList array. If you need to, you can probably increment price at this time too.

The problem would be if permissions didn’t let you edit the drink’s variables (toppingList, drinkPrice, etc)? I don’t think that’s an issue, but I haven’t seen the code. Flowcharts like this book is littered with are really helpful to understand the design patterns, but they just don’t give you (me, anyway) the whole picture.

But if you did implement new toppings, you would have to go back and add support for them wherever the toppingList array is evaluated (near the end of the program, I think), which is something you’re supposed to avoid. Maybe you could hack around that, though. It would still leave your objects in a more usable state regarding how much information you can access from them.

Again, I’m still on my first, light run-through of this book, so there’s a lot I don’t know. If you’re not already familiar with design patterns and what is good practice, don’t let my speculative discussion teach you bad practice.

A few more projects

I’ve started teaching Python to my 12yo. brother Ben. He picks it up really quickly and asks the right questions; his problem is that he doesn’t make the mistakes that the Python book keeps trying to get him to make, the ones he’s supposed to learn from. He’s already meticulous, so if I don’t intervene and point out all the ways you can screw up a program, he won’t have the experience of knowing what it looks like when you do make stupid mistakes. Because everyone makes stupid mistakes in programming. It’s just a thing that’s going to happen, no matter what.

So far, the design patterns book I’ve been reading has covered the Strategy pattern, the Observer pattern, and the Decorator pattern. I like Strategy and Observer, but I don’t like Decorator. I keep getting this feeling like… I would do it differently, use more of a Strategy-shaped design. The book keeps talking about a “Factory” pattern; maybe that’s what I’m thinking of but can’t pin down. I just don’t like Decorator on its own. It seems kind of unnecessarily complex… obtuse… clunky. Maybe I’ll like it when combined with Factory, or maybe I don’t understand it well enough to get why you’d want to do things that way.

Meanwhile, the book is teaching me more about OO principles than any programming book I’ve ever seen. Between Head First Design Patterns and Google, I’m seeing a lot more of what you can do with objects via example than is ever really explained in other contexts. School teaches you to type

public static void main (String[] args) {  }

(or equivalent for non-Java languages) but never actually shows you a program where you use publicly-accessible methods from another class; I’m still not really sure what static does. They teach you what classes and objects are–sort of–but don’t teach you how they can really be used. They don’t teach you what an interface is, or how libraries actually work. They teach you syntax and how to solve toy problems. I have a feeling I’m going to end up teaching some other new programming grad I’ll have to work with about everything the classes missed. In fact, if I can find the patience to type these things up, maybe I should post them here.

I can see my own progress by the fact that the source code for Tetravex, which I downloaded on my Debian VM, is now magically understandable. Not sure how that happened, but there are a few bugs I want to send in a patch for–if they haven’t already been fixed. If I do that, it’ll be my first contribution to open-source. 🙂

Design Patterns

After taking a kind of quick course in some of the finer points of OO programming, I’ve come back to the design patterns book I had my mom buy for me recently.

It’s this one:

Head First Design Patterns cover

 

(Clicking the image will take you to its Amazon page, where you can buy it for yourself if you want.)

Oh, a note before you do that, though. All the code examples are in Java, so you need to either be reasonably familiar with Java and its syntax, or with a similar language like C++ or C#. Although, quite honestly, if you’re familiar with some other OO language and clever enough to recognize patterns, I’d say you’ll probably be fine; take note that I haven’t finished the book, though.

 

I have to admit that sometimes I get bored with coding. Usually, this means one of two things:

1) I’m too stressed or burned out from working on other things, and my motivation for doing ANYTHING is next to nonexistent, let alone my motivation to work on complex intellectual activities like coding; or

2) I’ve been working on something that’s either too easy or too difficult, and I’m getting bored or frustrated, respectively.

I was getting pretty bored of working with the Python book. I found myself skimming stuff, wishing Shaw would just get to the point already… I think I’m finding that the point where you can just look at code and immediately see what it does means you have to move on, because you’re sitting in a kiddie sandbox. My 12-year-old brother will really find the book interesting, especially the simple game engine near the end, which was supposed to be one of the major final projects–but since I spent a lot of time when I was 12 fiddling around with RPG Maker XP*, my thoughts were more along the lines of, “Cute. Let’s move on.”

And it was time to move on. There’s a lot of stuff in this new book that I don’t know about, which I probably should know about before trying to get into it… but since it’s the only source where I’m finding any mention of these concepts, I’m just going to glark it from context.

Concepts like what the difference between a class and an interface is, and how the syntax for writing them is different… and then there’s this diagram system they use that I’ve never seen before… what “programming to an implementation” means… How come I’ve taken so many programming classes in OO languages, and they’ve never touched on this stuff?

Does all school work this way? You attend classes that teach you the easy half of what you need to know (or next to none of what you need, if it’s high school) until they’re satisfied enough with you to give you a fancy piece of paper, and then you go home and actually learn all your skills yourself? Mostly I’m annoyed on principle, as it’s not so much of a problem in my case–self-paced learning works really well for me–but it doesn’t for everyone, and that is super uncool.

An interesting thing I noticed myself doing while I was going through the Python book: I had read part of the first chapter of the HFDP book, and not really understood it despite trying very hard to do so, so I went back to the Python book. And as I went through it, I kept piecing together how the design pattern worked. So even though what I’d read was mostly Greek to me, having tried to understand it, it stuck in my mind anyway and I was able to use later clues to get it without even looking back at the HFDP book.

Of course, having returned to HFDP, it’s even a little clearer, although I don’t totally get everything the chapter has to say yet. Since this is a complicated book and I need to learn a lot of what’s in it from context (because I’ve never seen a lot of this stuff before and don’t know enough about it to even form questions on it), I’m doing two runs through the book. The first run, I’m just going to read it and try to understand stuff. I’m almost inevitably going to hit a point in the middle of the book where I get stuck and can’t understand anything more, and after that I’m going to skim. But I am going to go through the whole thing because, as mentioned above, stuff I don’t understand apparently sticks anyway if I wrestle with it enough. I didn’t think it would at first because it seems so complicated, but it does and the skill will develop more if I take advantage of it.

Reading HFDP is an experience. In each chapter so far, they present a problem that requires a design solution and they go through several different ways an inexperienced programmer might approach the problem, pointing out the issues and potential issues in each of them. Then they introduce their design pattern, not only coded properly but sometimes it even has extra features; not stuff that bogs down the code, but simply makes it more flexible. Objectively, but especially by comparison to the other code, the final solution is beautiful.

I don’t know if I can explain what constitutes beauty in code to my non-technical readers (if there are any? you guys must have patience). It can be achieving the best, most flexible results by the simplest, most minimal means possible even when the problem is complicated–in fact, that’s probably the most beautiful of code structures, something referred to as “elegance.” To be told your code is elegant is very high praise. Code beauty can also be achieved through ingenuity and creativity in design, although it’s still very important that the code be readable and maintainable, and most of all it should run. There are other ways for code to be beautiful, though, including code that is intentionally designed to do something ridiculous but actually manages to do it, or code that only works because of a loophole in the way the programming language itself is written (there’s a Jargon File example of this too, but I’m not sure where it is).

Head First Design Patterns’ solutions are the first kind of beautiful, which is the kind most worth committing to memory because they’re the most versatile. That’s the selling point of the book, really; that it teaches you good code structure, templates that are reusable, and then it’s your job to decide which one(s) you want and how you want to adjust it to your own needs.

Anyway, as much as I like writing and hopefully also encouraging other book-apprenticed coders and wannabe open-source junkies, I kinda want to go back to my book. I’m leaving this here for the day.

 

*If you’re not familiar with RPG Maker XP, think of it as kind of like Scratch (or, ostensibly, Alice, which I’ve never used), but more obscure and difficult to use. The map builder for the graphics part of the game is a lot like using virtual Legos. It runs Ruby, but since I didn’t know Ruby, I just used the game’s interface to generate the code line-by-line; its engine for that is closer to the code than the code-generating tools I normally get irritated with (like, you have to manage your variables yourself). I learned some programming logic from it, and a little bit of work with Photoshop for some graphics, but I never became very good at it. Nevertheless, I hammered away at the thing for hours on end, trying to recreate game versions of scenes from the fantasy novels I wrote (I was a weird kid).