In today's episode, we're going to define symmetry in code and identify three things to consider when identifying what tradeoffs we're making in our work.
If you have questions about today's episode, want to start a conversation about today's topic or just want to let us know if you found this episode valuable I encourage you to join the conversation or start your own on our community platform Spectrum.chat/specfm/developer-tea
If you're enjoying the show and want to support the content head over to iTunes and leave a review! It helps other developers discover the show and keep us focused on what matters to you.
Transcript (Generated by OpenAI Whisper)
Human's have a natural drive towards symmetry. This is something that arguably is driven based off of instinct. We seek symmetrical mates, for example, because at the genetic level, if you have good, surviving genes, genes that have few defects, then that produces symmetrical body shapes, face shapes, for example. This isn't true all the way across the board, for example. Human organs are not necessarily symmetrical. Our heart is on one side of the body. But it is interesting to say the least. Beyond just choosing our mates, there seems to be some kind of predisposition towards choosing symmetrical things when possible. What's odd is I tend to see this in my code, and perhaps you do as well. We're going to talk about how this may have a negative effect on the code that we write. It may have a positive effect on the code that we write. And like most things, they may be tricking us. My name is Jonathan Cutrell, and you're listening to Developer Tea. My goal in the show is to help driven developers connect to their career purpose and do better work so they can have a positive influence on the people around them. And in today's episode, I want to discuss this idea of symmetry in our code. What exactly would it mean for your code to be symmetrical? That's perhaps the entire discussion for today's episode, because as it turns out, the way that we organize our code has a drastic effect on how we maintain that code. After all, pretty much all of code is about organization and naming things. A substantial portion of what we do in our code is deciding where to do what. So we should define asymmetry as it relates to code. And of course, a symmetry, if you're not familiar with the term, is being balanced, being somewhat equal on one side and the other. So you can think of a plain white piece of paper as being symmetrical, but you can also think of many other things as being symmetrical. And perhaps there are other ways that we are driven to symmetry, maybe not proper symmetry, but balance as a better stand-in for symmetry. So the human brain may make some kind of equality judgment, some kind of comparison judgment. And in fact, we do this quite a bit actually when we are purchasing things. We're trying to understand the trade-off. It's understanding some level of balance between one type of resource and another. This is an interesting comparison and it's something that we do all of the time, not only when we're making resource trade-offs, but when we're comparing any two things at all. In fact, it could probably be argued that the human brain's kind of default mode of understanding the world is in terms of relationships, in terms of comparison. So even in regards to our social scenarios, the first thing that the brain does is it compares it compares ourselves to others, it compares others to others. This is just kind of the natural way of existing for our brains. Now, again, this goes back to our kind of instincts and our ways of sizing up the world. It's difficult to do it from some objective position. So we take a subjective position, we try to create sense out of the world by comparing things. So, what does this all have to do with our code? Well, you've probably tried to make your code symmetrical. You've probably tried to create balance in your code. And this can have all kinds of effects. It's not necessarily a good or a bad thing. It can take good things out of this drive toward symmetry. And we can learn about bad things that this drive toward symmetry could create. And finally, I want to dispel the ideas of maybe false symmetry in your code. But first, I want to talk about today's sponsor, Digital Ocean. What will you build with $100? That's what Digital Ocean is going to give you, incredible, to get started on their cloud platform. This is the easiest cloud platform to run and scale applications from effortless administration tools to robust compute storage and networking services. Digital Ocean provides an all-in-one cloud platform to help developers and their teams save time when running and scaling their applications. With Digital Ocean, you get predictable and affordable pricing. And you can leave the complex pricing structures behind. You'll always know what your business will pay per month with industry leading price to performance ratios and a flat pricing structure across all of Digital Ocean's global data center regions. I encourage you to go and check this out because, especially because of this $100 credit that you're going to get, you can build your app with Digital Ocean. You'll get things like monitoring and alerting that are already included. When your app does indeed succeed, you'll have the ability to easily scale. You can rapidly provision new servers. There's just so many reasons to go and check out Digital Ocean. And of course, it integrates with all of the cloud orchestration things that you're already probably using. Go and check it out. D-O dot C-O slash T-E-A, that's D-O dot C-O, D-O dot C-O slash T-E-A. Thanks again to Digital Ocean for sponsoring today's episode. And that link is the one that will get you the $100 worth of credit when you check out D-O dot C-O slash T-E-A. Thanks again to Digital Ocean. So we're talking about asymmetry and symmetry, the balance and unbalance, the large and the small class or module, the big and the small service. These are things that we naturally want to make more similar. Maybe not necessarily cognitively decide that they need to look more like each other. But there is a proclivity, a natural drive towards symmetry that very often causes us to make decisions in code that we otherwise wouldn't make. There's also a positive effect of creating symmetry in your code. So let's talk about both of these. First of all, let's talk about symmetry and the illusion of symmetry in your code. It's easy to try to apply some static ruling to your code to make everything look similar. All of your classes should look similar. All of your methods names should look similar. The response time for all of the end points in your API should be similar. This is kind of a natural kind of homogenization, right? Symmetry between two things, but also symmetry across the full spectrum of things in your app. All of your line numbers should be similar. And there is a lot of realistic value to this. If you have symmetry, for example, in your naming structures, if one naming structure is similar in length, for example, to another naming structure, then you're going to have more readability between those two structures. Another thing that's important to note here is that if there is a difference, right, if one naming structure is significantly longer than the other naming structure, your brain is going to naturally ask the question, why? This is a bit of cognitive overhead. Why are these two things different? Your brain doesn't have to ask the question, why are these different if two things are similar? Right, this is incredibly important. If you have two things that are arbitrarily dissimilar, if you have two things that perform similar jobs, but have unique characteristics, right? You're using camel case in one and you're using snake case in another. If you have things that have arbitrary differences, your brain is going to try to parse those differences, try to give meaning to those differences. Sometimes those differences are meaningful. And that's what we're going to talk about in just a moment when we talk about choosing a symmetry. And most of the time, the code that we write, if we create symmetry in most respects, there's a positive outcome to that. But moving beyond syntax, we may also feel that certain types of software design require symmetry between the various parts of that design. Whether you're using component architectures or class architectures or even functional programming, the idea that one class should be similar to another. This is actually one of the reasons why, especially in object oriented programming, people are fairly reticent to create a new class. In the average program, object oriented program, you're going to see classes holding significant amounts of data and behavior. You're going to see classes used for significant concepts. And so it's hard, cognitively speaking, to create a class that has much less information, much less behavior associated with it. And yet perhaps one of the most powerful things you can do in object oriented programming is create a series of smaller classes. And this is true with component design as well. We can imagine that components are of a certain size. And we all have heard conventional wisdom that once a class grows too large, then that becomes a problem. And we have this concept of God objects. Very often people will refer to, for example, users, user is a God object of many applications. And this can very clearly become a problem. Because instead of having, let's say, 100 lines, you have a thousand lines in that class. And we can immediately see the problem with this. We can see that a very large class is a problem. And so on the flip side, we don't see very small classes as a problem, but we also don't see them as the solution. Usually we imagine that a class lives in a certain range, that a component lives in a certain range. And this is really kind of fundamentally the argument that this episode is making, that one of the reasons that we see these components, classes, functions needing to look similar to each other in terms of the amount of behavior that they're responsible for or the number of methods that are in that class or how much surface area does this component take up. Perhaps one of the reasons that we have those definitions is this drive for symmetry. And I'm here to encourage you to seek asymmetry when it is useful. Allow yourself to create small classes, create small components. Allow yourself to create a module that has only one method in it. Sometimes these small pieces that are totally asymmetrical when comparing them to other pieces in your code, they can be incredibly useful. It's easy to allow these larger classes, larger objects, larger files to act as kind of magnets. Imagine the idea that a large planet has a lot of gravity. And it can easily suck in smaller orbiting pieces. And the problem is, when we start allowing too many of those small things to get sucked into those larger pieces of the code for the sake of symmetry, we lose some of that information. That information we were talking about previously where our brain sees the asymmetry and it tries to understand why. Why are these two things different? This is kind of the unspoken messages that you have in your code that these things are different because they are actually different. They are not different because somebody was being lazy. Instead, the symmetry exists because that is actually more indicative of what this code represents. When we create false symmetry, when we inflate a class or when we choose to combine methods or combine functions into larger ones. Right often, this ends up being a kind of a vanity thing where our classes are quite similar. They feel good. The line links are similar and we can look through them and see how one relates to the other. But when it comes down to representing the domain that those classes or functions or components are responsible for representing things fall apart. And composability of those components becomes more difficult. Dependency injection of those classes becomes more difficult. So I encourage you to view symmetry not as an inherently good or bad thing, but instead as a tool. As a tool for both increasing and reducing the cognitive load for differentiating things that need to be differentiated. Instead of viewing these different types in your code, the types being things like classes or components or methods or functions or even variables. Instead of viewing those as having an opinion about the size or the nature of the thing that they are holding, view those as tools. Don't allow arbitrary symmetry. Don't allow artificial symmetry to have a negative effect on your code. On the flip side, be certain that when things are similar, that your code reflects that. Use symmetry to show the similarities between objects. Thank you so much for listening to today's episode of Developer Tea. Hopefully this resounded with you. I know that this has been something that has made my code design and review process significantly better and hopefully it will for you as well. Thank you again to DigitalOcean for sponsoring today's episode of Developer Tea. They're giving you a hundred dollars worth of credit to get started on their services. Go and check it out, d-o.co slash T-e-a. If you're enjoying today's episode, I encourage you before the episode ends to open up whatever podcasting app you're listening to right now, click subscribe. This is the best way to make sure you don't miss out on future episodes like this one. Thanks so much for listening and until next time, enjoy your tea.