Have you ever made changes to the code and just checked, rather than trying to fully understand the changes you made?

I work in a 12-year codebase on which I was the only developer. There are times when I will make a very small change based on intuition (or quantum leap in logic;).

I usually try to deconstruct this change and make sure I read the code carefully.

However, sometimes (more and more these days) I just test and make sure that it had the effect I wanted. (I am a pretty thorough tester and check, even if I read the code).

This works for me, and we are amazing (compared to most software that I see), a few bugs disappear in the wild.

But what interests me is that this is only the “artistic" side of coding. Yes, in an ideal world, you would exhaustively read every bit of code that changed your change, but in practice, if you are sure that this affects only a small section of the code, is this normal practice?

I obviously see that this will be a catastrophic approach in the hands of a poor programmer. But then I saw programmers who supposedly read the code and break the material left and right (in their own code, which they only work on).

+4
source share
8 answers

Once you wrap the legacy code in a secure DOUBLE safety blanket (good unit tests and good system / integration / regression tests, with excellent coverage from each of the two levels), relying on tests to catch the wrong ideas is an effective short-term tactical approach. This is part of adding tests to an outdated code base with a high ROI strategy: it allows you to make urgent bug fixes or add burning-urgent functions faster, giving you reasonable assurance about the validity of changes made without a deep understanding of the subtleties of existing code.

However, as other answers hinted, such changes accumulate technical debt; as for any other debt, the sooner you pay it off, the better it will be in the long run. In this case, “payback” is not only documentation of internal components, but often it can be to refactor code for clarity and malleability - really good tests will help you to make such refactorings with confidence, just as they are for fixing bugs and improving the functionality of outdated code.

+3
source

This happened to me once in a while. But I would like to emphasize the moment that the other person mentioned in his comment.

  • No matter what you understand, try to document it. You can save yourself and others a lot of time with the next change.

And for my two cents it’s worth ...

  • You mentioned that you “check” your work and compare it with previous results. A few years ago I read a guy who was trying to argue that the most valuable thing a company can own is not the code itself, but tests (i.e. JUnit). He said that throughout the entire software life cycle, the code will often change - from minor fixes and improvements to complete rewriting. With maturity and experience, I understand what he means now, and try to use his advice. In test cases, you can prove that your new job is functional and will not break anything. My point is ... try to save and reuse any test you may have. Some programmers tend to sometimes remove these tests. They will become extremely valuable later when other programmers make changes as well.

Happy code change,

Jeach!

+3
source

Sometimes changing the code and testing helps to understand the code. Of course, you always step on dangerous ground when you make changes that you don’t understand. I think that your success is based not only on your "experience", but also on the stability of the current code.
You can easily make changes to well-written code. But over time, this practice will catch up with you.
If you look at the code and you do not understand it, it is time to figure it out and document it. Otherwise, every other programmer will have to understand this when they need to make changes. It’s better to do it once, fix it, and save time and hassle for everyone in the future.

+2
source

I, most likely, are not the intended purpose of this question, since I have only been a professional developer for several years. However, I will throw my 2 cents anyway.

I do it ALL TIME. When I am in a tight deadline, I get code that works reliably regardless of whether I understand all this or not.

Usually I try to come back later and see what I did - usually on the weekend - and update the code to reflect any bad decisions with copy / paste code. But the deadline is the king, especially if the contract contains fines for its absence. You can always send an update that fixes any problems later.

+1
source

Constantly!

0
source

You want your code to consist of small pieces that you can test and understand separately.

Each small part should do one thing and do it well, regardless of whether this part is a function, and a method, or a class.

You want to be able to assemble large pieces of functionality from these small pieces so that each composition, no matter how complex internally, remains simple at the level of abstraction of that functionality.

In other words, even at a high level, we should still be able to describe complex internal elements in simple external models.

This is what Andrew Koenig says when he says: "Abstraction is selective ignorance." By deliberately abandoning the knowledge of how something wmay works inside, we may not consider how it works, but what it does.

Let's give a brief example. At the top end, we could say: "this class will find the smallest int in some data structure." This tells us what he does, not how he does it, and at this high level of abstraction, that we all care.

We have something that does something, and its modular, we can replace it with something else that does the same, no matter how it is done. It has an open interface.

Now at a lower level, it may happen that this is due to the fact that inside it is a heap, or a priority queue, or something else.

And these things can be implemented in terms of trees or self-balancing trees or even (under the optimal) linked list. The linked list will be a suboptimal implementation, but until he did the same, we would not be a cafe, because if suboptimality came back enough to slow down our program, we could exchange it for a better implementation with the same interface.

And these things are implemented in terms of traversing the tree (pre-order: always go in the order on the left, parent, right). And these things are implemented in terms of simple operations on nodes.

And here is the important part: since the rest of the application has nothing to do with the internal or side effects of this module, the swap is from a worse implementation, since the best of them does not change any of our other codes, it simply speeds up the work.

Each level is associated only with layers located directly above and below it, so that each layer can be replaced. Visually, it looks like circles inside circles inside circles, and not like overlapping Venn diagrams.

If you need to rely on intuition, it means that your code has side effects, or that it has too wide interfaces for other modules, or that instead of interfaces in general, instead of code created by stand-alone, disjoint modules, you have overlaps and intersections and fragile code. That you do not have it broken into pieces is simple enough to understand.

(Shit, late, and I'm afraid that I might break this explanation better. I will come back to edit this.)

0
source

No, I never do that. I expect my code to be 100% logical and error free, and it will be read by other people for years to come. The whole concept of incomplete understanding of the context of my code seems dangerous. And reading code should be the fastest way to determine the exact operation of the system. If this is not the case, I suggest you something is wrong with the quality of the code.

While I am reading, I am also studying. I think the hell is interested in the fact that the system I'm working on is an important part of my professional standards. With this curiosity comes the ability to develop the system and improve it. If I could not do this, I think that the development will be very boring.

0
source

If you change a method, you must test it thoroughly, including methods that call this method.

0
source

All Articles