Author Archives: wurmpress

Putting the ‘O’ in SOLID


We
covered the Open/Close principle in a recent lab, and it prompted a desire to
cover some of the SOLID principles. I have determined however, that the length
of this blog is short enough that I should dedicate it to a single principle at
a time, beginning with the aforementioned Open/Close principle.

              This particular object-oriented
principle was outlined by Bertrand Meyer and states:


“…entities should be open for extension, but closed for modification.”


              This of course, is a complex way
of expressing a simple guideline for software development; which is that new
functionality should be able to added without having to radically change existing
code. The operative word, extension, is illustrative. If your code was a home,
and you wanted to add more square-footage (read: functionality), you shouldn’t
need to knock all the walls, or the whole thing, down to add a bathroom.

              In the blog chosen, the author summarizes
a talk he gave about the very subject. In it, he provides an example of a program
he is developing for a company that calculates the total area of a set of rectangles.
As the customer requests more and more shapes be added to the calculator, the original
code changes drastically and gets longer and longer. This modification is opposed
to this principle. In opposition, creating a Shape class that contains many children
of different specific shapes – each with their own area function – with the
ability to add more, eliminates constant modification of the main class, and
allows for constant extensionability in the form of new shapes.

              To say simply that code should be
modular is unhelpful, as it is broad and the general definition of so many more
good coding practices. Our class and homework provide another perfect example.
Why should we have to constantly Override and rewrite portions of a superclass’
methods in each of its child classes to achieve proper functionality. Instead, in
making a Quack/Fly Behavior interface we have established a broad mold that
many new behaviors can be built off of; access to all of which is then granted
by the relationship to the single respective behavior interface.

              Therefore, the ability of code to be
extended with new functionalities, using a single reference – in this case the behaviors,
or shapes – instead of needing to rewrite or overwrite code is what is meant by
extension; while keeping the existing code from needing constant revisions, is being
closed for modification. Like the house example earlier, you should constantly be
building out, not renovating what exists already.


Sources:

A
simple example of the Open/Closed Principle

From the blog CS@Worcester – Press Here for Worms by wurmpress and used with permission of the author. All other rights reserved by the author.

Static VS Dynamic Testing


In Software Testing, the two
most popular or important methods for testing are static and dynamic. While both
are obviously named, its good to go over the distinctions, and more importantly,
the actual implementations of both.

           Static
testing involves review of project documents, including source code, to weed
out any actual or potential security flaws and general mistakes. This takes the
form of Informal and Technical Reviews, Inspections, Walkthroughs, and more. This
process can involve an inspection tool or be performed manually, searching
for potential run-time problems, but not actually running the code. Dynamic testing
conversely involves actually executing code looking for functionality,
resource usage, and performance. We have been using dynamic testing, specifically
unit testing, in our class so far. Dynamic testing is used mainly to verify the
program runs in accordance with the specifications outlined for it, specifically
called System Testing.

           Of
course, both have their own advantages and disadvantages. In static testing you
have the potential to find bugs that may have made later development more
troublesome early in the process, which can save lots of time and frustration in
the future. However, there may exist some flaw that only a running program can
reveal, but it only in the code that is executed. It would seem to me, that
these should not be exclusive and in fact, they have a logical order.

           You
would begin with static testing, like proofreading a paper, searching for misspelled
words (poor variable/method names), run on sentences (needless complexity or
repetition), and reorganizing to best get your point across (logical order of
declarations/methods, documentation). Like writing a paper, it is best to do
this ahead of run-time (reading through), that way you don’t have to constantly
stop to bandage small errors. In the same way it seems essential to ‘proof-read’
your code before execution to make sure it is free from identifiable errors
before you move on to seeking out run-time errors. You wouldn’t want to have to
fix both at the same time like with proof-reading.

           In sum,
these two could be grouped as pro-active or reactive, static and dynamic respectively,
and best explain their use. As mentioned, these also make sense to utilize in a
specific order, ensuring code is as correct as possible upon inspection, then
running it to see where flaws undetectable in a static environment have arisen.
These together ensure quality software that is optimized and secure.

Static Testing vs Dynamic Testing: What’s the Difference?
Static Testing vs. Dynamic Testing

From the blog CS@Worcester – Press Here for Worms by wurmpress and used with permission of the author. All other rights reserved by the author.

Refactoring: Spring Cleaning for Code

Depending upon the subject, some of us are lucky to finish a functioning project so the thought of improving code after the fact – especially if there’s a new project due soon – is a distant one. However, they may be tricked into refactoring their code if asked when you say the magic words: “Refactoring is not rewriting code”. The definition, as defined by its creator is:


“a change [or changes] made to the
internal structure of software to make it easier to understand and cheaper to
modify without changing observable behavior.”


In
reality, the process may involve:

  • new
    code, but it must not change the behavior of the original code;
  • ensuring
    the system works before and after each refactor, including original unit tests;
  • creating
    unit tests to verify our refactoring has not changed system behavior;
  • changes
    that individually are minute, but combined lead to a healthier program;
  • eliminating
    duplicate code, potentially changing variable names, and more.

It is not
simply cleaning up code, but rather reorganizing it in order to make it easier
to trace and understand, as well as add functionality to in the future.

              For our purposes, this may be a very
important concept to learn but it may be some time before we get to implement
it, unless we’re coding or maintaining an entire program for our capstone; however,
it is important to understand when to do so. According to my sources, the best
time to do so is before you add new features to an existing program, or right
after you’ve already shipped it. For the former, it makes these new features much
easier to add when the program is much more readable and makes the program better
for having made the changes. As for the latter, it makes a lot of sense to
snoop around for ways to reorganize code after you’ve spent so much time on it,
and in a mad dash to finish it towards the end no doubt. Years’ worth of work
is no doubt going to have some inconsistencies that fell through the cracks in
the course of development.

              As for implementing these changes, there are several methods, including Red-Green-Refactor, Abstraction, Simplifying Methods, as well as many others we won’t cover. In R-G-R, red means stop and determine what to develop – usually with a new test that fails, getting this new development to pass tests (green), and finally refactoring to optimize. Abstraction is used to address duplicate code and can be done by restructuring hierarchies using the Pull-Up [pulling up code into a superclass to be shared more effectively] or Push-Down [pushing down code to more subclasses from a superclass] method. Finally, Simplifying Methods is an effort to simplify older code by consolidation and reducing interclass complexity. Hopefully this helps develop an understand of refactoring, in fact, I had to do quite a lot of refactoring to this blog to get it down to size!


Sources:

Refactoring – Martin Fowler
Refactoring – Agile Alliance
Code Refactoring Best Practices: When (and When Not) to Do It

From the blog CS@Worcester – Press Here for Worms by wurmpress and used with permission of the author. All other rights reserved by the author.

Thinkin ‘bout KISS‘n you


KISS
(Keep it Simple, Stupid) is potentially one of the most culturally pervasive concepts
used in Computer Science, the other being maybe blockchain – the difference of
course is that people actually understand what KISS is, everyone who says they
understand blockchain is lying. Of course, KISS did not originate in Computer
Science, and instead was popularized at Lockheed Skunk Works by noted
tangential war criminal and engineer Kelly Johnson. While it may be difficult and
seemingly sacrilegious to try to explain something so self-explanatory that is
what I hope to do, flying in the face of the concept of simplicity to stretch
four words into four hundred.

Credit: csiaexchange

              It begins with, put kindly, making
distinctions about the semantics of the scant few words in this phrase; put
more bluntly, being pedantic. This examination is important, and the linked
article does a great job of highlighting first the distinctions between ‘simple’
and ‘easy’, which could be mistaken as synonyms, and contrasts it with ‘complex’.
His conclusion is this, a simple system is defined by what it is not, which is one
with too many parts which are interconnected – with the latter being worse in
software development.

              This all sounds wonderful on paper,
and about the same on a computer screen, but sometimes complexity is
inevitable. So, it is advised that you make things as simple as possible, until
you can’t, at which point you are vigilant in handling that necessary
complexity. For instance, I could try all sorts of methods to navigate a 2D
array in some mock-up code, but I don’t need to introduce recursion or anything
outrageous to shorten a method body if a simple nested loop will do.

              This idea of simplifying through pruning
code is expressed in the next sections of this post, stressing the importance
of cleaning up dead or underutilized code so that no resources are wasted maintaining
or reintegrating useless code. Additionally, YAGNI (yay more acronyms) states
more or less the same thing, encouraging programmers to implement the essentials,
that will actually be presently utilized, and skip the bells, whistles, and
maybes. Code with bunches of maybe methods require time and resources to
maintain and if they aren’t actively being utilized, then they’re a waste of
both.

              From here on, the blog introduces
many more concepts that are possible to cover in just this blog post – although
I do hope to mention Lasagna Architecture in another post sometime later. Instead,
I think it is time to bring this post to a close. What is the take-away then?
Well its exactly what you thought it was from the first line. In conclusion, it
may be appealing to get a jump on features you may want to implement in the future,
but it is best to keep things as simple as possible and/or only as complex as
needed but no more.


Sources

KISS Principle Explained
KISS, A Design Principle

From the blog CS@Worcester – Press Here for Worms by wurmpress and used with permission of the author. All other rights reserved by the author.

Anti-Pattern Cannon


“…an
atomic plant is so vast, so expensive and so complicated that people cannot
grasp it, and rather than try, they fall back on the assumption that somebody else
checked all the details before it got this far… A bike shed on the other
hand.  Anyone can build one of those over
a weekend.” –
Poul-Henning


While the blog post I have chosen
does not lead with Bike-Shedding, it is certainly one of the most interesting
examples of “Anti-Patterns” – practices in programming that are counterproductive
to both actual development as well as implementation – and provides a hilarious
anecdote, of which the quote above is from. While perhaps less entertaining, this
post outlines nine types of coding Anti-Patterns and defines what they actually
are, why they are bad, how to avoid them, and provides – my favorite –
examples, among other notes. Most importantly, these concepts are tied to code
smell, and I hope to explain the links between code smell and the practices
that cause it.

Credit: refactoring.guru

For instance, the first Anti-Pattern is Premature Optimization: As the name suggests, it is trying to code for bottlenecks you may have rather than using tried and true methods and finding the actual bottlenecks on runtime. As mentioned, in my own code I have a similar problem where I attempt to write everything perfectly, or in as few lines as possible, instead of building a working a prototype and then cleaning up code after review.

While perhaps not identical to this pattern, the tendency to get hung up on all the possibilities and edge cases just slows development and often the actual execution of the code. Code that has developed in this way is very similar to a code smell known as Speculative Generality, which is defined as excess code created “just in case”. The only difference is that instead of excess optimization code this smell is more interested with future features.

Another relevant example is the God
Class: a single class that contains and controls aspects for an excessive
amount of child classes. When code is structured in this way it makes maintenance
an obvious nightmare. This reflects two code smells most closely, Large Class
and Shotgun Surgery which are tremendously large classes that need to be split
into smaller pieces and the need to fix smaller problems spread across several
classes as a result of another change, respectively.

Credit: refactoring.guru

This trend continues with the Fear
of Adding Classes pattern reflecting the aforementioned Large Class smell;
Useless Class pattern and Lazy Class smell; and the trend continues. What I
wish to express mainly is that these two concepts exist on a continuum with Anti-Patterns
on the development end and code smell on the completed program end. So as we move
forward with the course I’ll try to be cognizant of the Anti-Patterns that lead
to poor code – as well as those which slow development cause of interpersonal
issues which I didn’t get to discuss in this particular post – and how this
poor code exhibits various code smells.


Sources:

From the blog CS@Worcester – Press Here for Worms by wurmpress and used with permission of the author. All other rights reserved by the author.

AN INTRODUCTION

Despite the foolish blog title, this blog will hopefully be anything but; and not just for your sake but mine as well, as I’m being graded for it! I will be utilizing this blog for documenting both CS343 and CS443 class work and sharing other CS-adjacent content that I’m working on.

As such, it is appropriate that I introduce myself: My name is Brandon, I’m a senior CS student, doing both Software Development and Big Data Analytics, and am the PAL tutor for CS242 this Fall semester. If this blog is any indication, I like to keep things light, I love getting out, either up a mountain, on a lake, or bike trail. Between my job building computers and school I get plenty of time indoors as well.

OLYMPUS DIGITAL CAMERA

I unfortunately have not had much time to pursue independent studies or projects but I’m hoping after graduation to build my first program, likely in Windows, as well as my own professional website. No offense to WordPress but I don’t think this will bolster my portfolio.

Well I’m not sure how to end this so what if I did with my cat?

From the blog CS@Worcester – Press Here for Worms by wurmpress and used with permission of the author. All other rights reserved by the author.