Tuesday, October 25, 2011

The Art of Shining within Steel Confines

Freedom in America doesn't come cheap. You still have to follow the laws within society, which are as strict as steel, in order to be considered a good and civilized citizen. The same goes in the software engineering world. Most of you will find yourselves in a business that is not run by you. There is little freedom to code in whatever way you desire or to say no if a software review is requested of you when you have so many other matters of importance to attend to. Midway through this semester, I've learned that I've missed out on so much over the past two years. I thought that if I followed the norms and did all that was required of me in my classes, I'd be on the road to success. Apparently, that thinking had always been far off-key. The following questions and my answers to them reveal that shining within steel confines is an art, not a sequential computer program as I had thought it to be all along.

1) What is the difference between standards and feedback? What are the many ways in which you receive feedback in this class?


Standards and feedback are vital for the three prime directives of open source software. Standards are required to allow people to work together in a way that would eliminate unnecessary unexpected events and technical issues. With standards in place, people can worry less about doing the right thing and focus more on the quality of their communication with others. Feedback, on the other hand, is the key to improvement. Success in the software engineering world is not an end goal but constant improvement. With constant feedback, success can be achieved. While standards provide structure, feedback shapes personal and professional growth. Ways in which we receive feedback in class are from partners or group members, other class members, the professor, the designated mailing list, automated quality assurance tools such as Checkstyle or FindBugs, and the outside online community.

2) List the four ways in which your professional persona is assessed in class and elaborate on each of them.


Your professional persona is how the world views you as a professional - a person with valued thoughts and valued skills. Here are the four ways in which professional persona is assessed in class:

1. professional portfolio - A place you can boast all about yourself (and only yourself). Do so in a professional manner, of course. This means no going into endless anecdotes about your personal life. Instead, highlight your industry-relevant skills and achievements. Detailing projects you have worked on is valuable, as it could give potential employers deeper insight into what you're actually capable of.

2. online engineering log - A blazing hub for your professional thoughts on industry-relevant tools and matters. This time, the focus is not on yourself but on those tools and matters. Write for the world, but keep in mind that your target audience is potential employers. They would use this log to assess your ability to communicate effectively through writing.

3. participation in professional social networks - A portal into valuable unending knowledge. This allows potential employers to witness firsthand how you contribute to industry-relevant discussions and how much you care about colleagues and others in the business. Furthermore, this will contribute to your personal and professional growth, giving you a broad range of views that you simply cannot obtain from just working with one or a few companies.

4. participation in open source projects - A concrete showcase of your expertise. Anyone could say they could write code, but the question in most employers' minds is, How well could you write code? Open source projects allow employers to examine actual code you've written and shared with the world. It also gives them an idea of how well you assimilate into a group mold: Do you follow your own standards or the standards of the existing code?

3) Name one way, outside of class, that you are encouraged to enhance your professional persona. How would this benefit you?


Participation in technical societies and activities would only further enhance your professional persona. Such technical societies include IEEE, ACM, SWE, and Honolulu Coders. Some technical activities are to chat in the IRC, compete in TopCoder competitions, and practice information security skills on wargaming websites such as SmashTheStack.org. Participating in any of these and more is a remarkable benefit because you could gain skills and knowledge that you would otherwise not gain from reading a textbook or taking a class. Such participation gives you a lot more to talk about during job interviews. In addition, if you win in a technical competition, you could add that to your resume and professional portfolio.

4) What are the three questions to ask yourself when conducting a software review? Why is each of these important?


A software review is a vehicle for further growth of technical skills and knowledge. The ability to assess others' coding faults is crucial and helps you to better assess your own code. In addition, the software engineer's code you're reviewing may have functionality very much different from your own, even if the two of you are working on the same product. Therefore, in the long run, it's always best to understand at least the key functionality of the code you're assessing as well as where the vulnerabilities may lie so as not to repeat the same mistakes and gain a better understanding of the product as a whole. When conducting a "decent" software review, here are the three questions to ask yourself:

1. Is my review revealing problems?
Importance: A software review takes time away from writing more code. Why conduct a software review when it won't be accomplishing its purpose? Its purpose, in fact, is to reveal problems with someone else's code - problems they easily skip over or normally can't find on their own. On the job, it's a business because time is money. In general, make sure what you do is relevant and that you achieve the purpose. Otherwise, you're not helping the business, the other software engineer, the customers, or yourself.

2. Is my review increasing understanding?
Importance: What good is a software review when all you've written sounds like gibberish to its target audience - the software engineer who has written the code? All your efforts to improve the system would go to waste if you won't take a little extra time and effort to enhance the software engineer's understanding of their own code. In the process, you will only be helping yourself feel better about yourself for helping someone else and feel better in general for gaining deeper insight into the product under development.

3. Is my review doing (1) and (2) efficiently?
Importance: Yes, take a little extra time and effort - but not a whole lot! The key to "time is money" in a business is balance. There should always be a balance between every component of your role on a software development team. What good is a software review that takes two weeks to complete when a report summary of new updates to a system is required each week? Be able to use good judgment, common sense, and past mistakes to assess how long a particular review for particular pieces of code should take.

5) Give some examples of why the saying, "It's [the professor's] way or the highway," is quite prevalent in this class and relate it to the real world.


Part of the answer lies in the introduction to this post, in which there is little room for freedom when software engineers must conform to standards and follow norms. But of course, without it, chaos would ensue. As we all know, understanding and debugging another's code is quite different from doing so with your own. For the purposes of this class, one example of "the professor's way" is our use of the Eclipse IDE, which goes hand-in-hand with our use of Java. Eclipse is used mainly because it runs on multiple OS platforms, it is free open source, and it is easy to integrate its use with other tools (such as Ant, JUnit, and SVN). We code with Java, even though there are so many other useful languages, because it is one of the most supported languages today with a complete API and a smorgasbord of tools at its disposal. I can very well imagine if we were allowed to use other IDEs or languages in this class - we would certainly get less work accomplished and acquire software engineering skills and knowledge at a much slower rate. In relation to the real world, the chaos and destruction would be tenfold and much more serious and irreversible. Nevertheless, there's an art to shining within steel confines: Follow their way and never take it to scorn. If you learn what you can outside the edges, you're paving the highway and calling it your own. In time, others will recognize you for it.

Thursday, October 20, 2011

Submersion into Subversion

These days, when we hear brand names such as Apple, Microsoft, and Google, we think of one software, one hardware, one product. We hardly stop to think of what lies past the name, past the "one." But in fact, it is a multitude of people who makes a product, not just one company. And they make a product in time for its launch date, continuing to provide updates and support afterwards. Let's focus on the software for now. How is it possible not to transform into some wild green-eyed lost soul due to millions of lines of code, written not just by you, but by others as well? The answer lies in configuration management.

Configuration management tracks the state or configuration of a system at any point in time so that changes made to the system are logged and different versions of the system, old or new, can be utilized for different purposes. Configuration management aims to solve the issues that arise when multiple programmers work on a single software product simultaneously. Even with simple compilation or verification issues, the quick fixes may not be apparent until hours or days into debugging. But with a configuration management tool, this could be avoided, since the previous version of the system, before the incriminating changes were made, could be downloaded.

Google Project Hosting and SmartSVN for Mac (TortoiseSVN for Windows) is an excellent duo for amateur developers to kickoff with configuration management. Add Robocode or a working project into the mix along with classmates or friends for committers, then you could host your very own project in no time. Including easily accessible User and Developer Guides is the standard and allows others to know that you intend to treat them and your work on a professional level. The checkout URL repository on Google Project Hosting appears under the Source tab, and Subversion (SmartSVN or TortoiseSVN) provides the host and committers with commit and add access. The Changes link under the Source tab and the Updates link under the Project Home tab display any changes made on the site.

Overall, this was quite a refreshing learning activity and was none too difficult at all. The only minor hurdle was the initial attempt to get my project files uploaded to the trunk directory of my robocode-bma-[nameofrobot] project. Otherwise, brief communication with my classmates and watching the screencasts made this an easy dive into configuration management.

Tuesday, October 11, 2011

A Prime Example of What It Takes to Not Win at the Robocode Tournament

1. Overview
We have all been recently promoted to a belt of the next higher level and have now been asked to compete in the once-per-course Robocode Tournament. Am I strong enough? Have I trained enough? Do I have what it takes? Well, it was time to take one step at a time and see for myself.

To start off, I used the Robocode Katas Assignment as a foundation upon which to build my competitive robot. Notably, I made use of HitWallEvent from Position02, movement from Position04 and Position05, and firing tactics from Boom03 and Boom04. Of course, bunching all this code up together in a single robot is not ideal. So I then focused my efforts on beating one sample robot at a time.

In an ideal world, my main objective would be to win the Robocode Tournament if I had had more time to work on this. However, lack of extra time was indeed the case, and so, my main objective was set to the minimal requirements: to defeat the eight sample robots, namely, SittingDuck, Walls, RamFire, SpinBot, Crazy, Fire, Corners, and Tracker.

2. Design
A. Movement
My robot's basic movement is that it always moves to the center at the start of a round, so as to maximize its chances of getting closer to the enemy robot, since the closer it is, the greater its firepower. The only other time my robot moves is when it dodges (moves ahead by 100 pixels), if the following two conditions are met: its distance from the enemy is greater than 200 and its energy is less than 40.

B. Targeting
In the run method, the radar constantly turns in the while true loop (but this only happens if the robot hasn't chosen a target yet). Targeting is calculated with a simple equation in the method trackTactic: my robot's heading minus its gun's heading plus the enemy's bearing. The gun should only turn towards the enemy if it is not already pointing at said enemy. For some reason, however, my robot still turns its gun at times even though it has been constantly firing at the enemy who has been standing in the same location.

C. Firing
An enemy robot is fired at once it is detected. My robot's firepower has strengths 1, 2, and 3; the closer the enemy is, the weaker the firepower, and the farther the enemy is, the stronger the firepower.

Beating one robot at a time:

R1. SittingDuck
A no-brainer. This robot doesn't do anything, so there's no strategy required in beating it.

R2. Fire
My code for beating Fire certainly isn't the most efficient implementation. But it works. Fire helped the logic in constructing the onHitByBullet method, which triggers a HitByBulletEvent if the robot is hit by a bullet. The bearing of the bullet is the direction in degrees relative to my robot's heading. Basically, if the robot is not facing the bullet dead on, just move forward by a few pixels. But of course, if the bullet is hitting the robot in the face, turn right by a few degrees before moving forward.

R3. RamFire
While the Fire sample robot centers on the onHitByBullet method, RamFire centers on the onHitRobot method, since that is exactly what RamFire does: hits the enemy robot. I tried firing twice with a maximum power of 3 and to my surprise, it beat RamFire a few times. However, I wasn't satisfied with two lines of code, so I had my robot fire only if its energy was greater than or equal to the enemy's. If my robot's energy was less, then it should back away. However, this tactic did not work well at all, since the extra time taken in moving backwards allowed RamFire to move forward in the same amount, corner my robot into a wall, and beat it to a pulp each time. In the end, I stuck with two lines of code that at least beat RamFire sometimes instead of never.

R4. Crazy
Crazy moves around a whole lot, which is good for evasion but not exactly a great evasion tactic, especially since my robot was able to win most of the time against it. I used a combination of two robot katas (namely, Boom03 and Boom04) to win against Crazy. The overall strategy is, the further away Crazy is, it's still good to try and shoot at it but with minimal firepower, since the majority of the time, my robot missed like crazy. And of course, stronger firepower was the way to go when crazy was nearer to my robot; it was the only time for redemption. Even though missing was still a high percentage here, getting in a few good hits was worth it.

R5. Corners
The tactics that Corners uses are simple but not quite strategic enough: pick any of the four corners, stay there, and shoot at the enemy. To beat Corners, I focused on the onHitByBullet method, since my robot seemed to be getting hit quite a bit. I noticed, however, that Corners only uses a firepower of 1. So instead of dodging all the time whenever my robot got hit by a bullet, I only made it dodge if its energy was less than 50 (half of the initial energy, which is 100) or if the bullet that hit it had a firepower greater than 1. Again, this is not the best strategy, but it beat Corners on more than one occasion.

R6. Tracker
Unfortunately, my onHitByBullet method worked for Corners but not for Tracker. Tracker follows the enemy and fires with maximum firepower of 3 at all times. Because Tracker always ended up close to my robot. This meant that even if my robot had more health and fired with maximum firepower at Tracker, Tracker would win because my robot would begin to dodge if its health was less than 50. This wasn't a good idea at all, as it always made my robot lose. So in the end, I created a boolean variable called "dodge" and initially set it to false, only to be true under certain conditions. In Tracker's case, dodge is set to true only if the distance between Tracker and my robot is greater than 200 pixels and my robot's energy is less than 40. But what really got my robot to beat Tracker was to change the requirement for maximum firepower of 3. By being more lenient on the requirement (the distance between my robot and the enemy robot is less than or equal to 300 pixels instead of 100), my robot had the upper hand on Tracker.

R7. Walls
I tried what I could against Walls, including using an onBulletMissed method to increase an integer count on the number of missed bullets my robot would fire. If this was above a certain number in the onScannedRobot method, then this would trigger a method to move my robot to a corner of the map. Unfortunately, before my robot ever got close enough to block Walls within its path, it often became an open target for Walls. I ended up having to delete anything to do with Walls. At this point, I don't think my robot can ever beat walls.

R8. SpinBot
At this point, my robot had enough basic skills to be capable of beating SpinBot on very minor occasions. The spawning location at the start of a round was one determining factor, as well as my robot's heading relative to SpinBot's overall position as he travels in circles. But in short, SpinBot was the victor.

3. Results
I used the two JUnit test classes for Corners and Fire to run 100 battles against each sample robot and calculated what percentage of the battles my robot won.

Sample robots that my robot can reliably beat:
- SittingDuck (100/100, 100%)
- Crazy (75/100, 75%)
- Fire (85/100, 85%)
- Corners (97/100, 97%)
- Tracker (85/100, 85%)
- RamFire (74/100, 74%)

Sample robots that my robot cannot reliably beat:
- Walls (0/100, 0%)
- SpinBot (7/100, 7%)

The detailed explanation of why my design worked for the majority and yet didn't quite work for some is located under the "Design" section, entitled "Beating one robot at a time."

In order to do better, I would improve my design by examining even more cases and setting more boolean variables or running counts on certain items, such as the number of times its bullets miss or the number of times it gets hit by a bullet. If the robot is in a certain state, then a particular tactic would be used instead.

4. Testing
I wrote two acceptance tests, two behavioral tests, and two unit test. The two acceptance tests simply test whether or not my robot beats Corners and Fire. The two behavioral tests test my robots movement and firing (there wasn't much strategy to targeting, so I left that part out). Lastly, the three unit tests checked to see whether or not my robot has dodged at least once in an entire battle and whether or not my robot has fired twice upon colliding into an enemy robot. Both JaCoCo and JUnit run successfully.

5. Lessons Learned
In future, instead of focusing all my energy into coding for one-on-one matches, I would develop strategies for matches consisting of more than two robots. In regards to software engineering, I have learned (from this project) that it is helpful to write about what you do along the way instead of writing about it after you are finished. This also minimizes error. From a software development perspective, I would definitely give myself more time to work on the project.