Category Archives: Tips

When a String is Null but Not Null

Introduction

A junior programmer on my team at work had an interesting bug.  Its symptoms I have seen more than once.  This post is what to look for and how to prevent it in the future.  I also explore different solutions to the problem.

Symptoms

The code in question looked well made.:

if(trouble != null && !trouble.isEmpty()) {
    System.out.println("fine here: " + trouble);
} else {
    System.out.println("not so fine here: " + trouble);
}

The code would hit the “fine here” block but would print the value of “null.”  The variable was set by reading a file.

Investigation

The developer and I looked at the print out and ran the test several times but the same result came up.  I looked where the variable was being set.  It should have set the value to null if there was nothing there, yet the print out stated the value was null.  I had an idea and we decided to test it.  He changed the code:

if(trouble != null && !trouble.isEmpty() && !trouble.equals("null")) {
    System.out.println("fine here");
} else {
    System.out.println("not so fine here");
}

The tests went to the “not so fine here” every time.  It appears the value was set to the string “null” not to the value null.

What to Learn

To tell the truth, I have seen this before.  It took me about a day when my code started doing the same thing to figure it out.  What I learned from this is that parameter checking is still a good thing.  I found that the valid string check could be used in several places in my code.  To prevent the copy and paste anti-pattern, I abstracted the validation into a method.

private static boolean isValidString(String test) {
    boolean isValid = (test != null && !test.isEmpty() && !test.equals("null"));
    return isValid;
}

The next step to prevent a longer and longer and validation line is to abstract it to a validation object.  This allows for a dirty word list.

public class StringValidator {
    private List dirtyWords;

    public static final int ARRAY_SIZE = 20;
    public StringValidator() {
        dirtyWords = new ArrayList(ARRAY_SIZE);
    }

    public boolean isValid(String test) {
        boolean isValid = false;
        isValid = (test != null) && !test.isEmpty();
        if(isValid) {
            for(String word: dirtyWords) {
                if(word.equals(test)) {
                    isValid = false;
                    break;
                }
            }
        }
        return isValid;
    }

    public void addDirtyWord(String word) {
        if(!isValidString(word)){
            throw new IllegalArgumentException(word + " is not a good dirty word");
        }

        dirtyWords.add(word);
    }

    private boolean isValidString(String test) {
        return ((test != null) && !test.isEmpty());
    }
}

which leads to this parameter checking code:

if(validator.isValid(trouble)) {
    System.out.println("fine here");
} else {
    System.out.println("not so fine here");
}

Conclusion

Sometimes we need to think a little outside the box to figure out a problem.  Don’t feel bad to get a second set of eyes on a problem; it maybe the best thing that happened.  I explored the solution ending up creating a validator allowing for the inclusion of a dirty word list without a long and confusing test. The source code for this can be found at https://github.com/darylmathison/null-but-not-null-example.

Advertisement

What I Have Learned So Far

Introduction

This is a list of what I have learned about the “soft skills” of Software Development.

1. It’s all about communication

Did you hate writing papers in school?  I did and so I just did OK on them.  I get into the real world and I have run into three things, reading, writing and talking; lots of reading, writing and talking.  I found out that technical writing is very different than English class.  I have to be concise,  clear and know my audience.  I don’t write the same if I am writing notes to my coworker that I have worked with for the last 5 years than if I am writing a blog entry.  I can’t waste time explaining flowery sentences to people.  You know what, I don’t have time to say the same thing 3 different ways so the next guy can understand.  That is why I am as clear as possible.  I make lots of pictures too.  A picture can explain a concept a lot better than I.  Writing papers in school prepared me to effectively communicate.  I can’t tell you how many times in how may ways I have explained things so a coworker can integrate with my code.  That leads to wasted time that can be dedicated to coding, testing, etc.

2. Knowing People

Did you know the hobbies of your coworkers?  If you did, you would learn something about that person.  Knowing that will help with number one.  I have a coworker that races motorcycles.  I have another one that likes to do computer forensics.  I approach both of them differently.  I also know that one of my coworker’s idea of an IDE is vi.  I approach him differently too.  Have lunch sometimes, you may learn something.

3.  Let it Slide

Do you have a coworker that really irritates you?  Do you have one that doesn’t agree with you on one or more points in software development?  Unless they are really getting in the way of you working, let it slide.  They are allowed to have opinions just like you.  Do you expect a bunch of yous running around?  That would be boring and the solutions you produce would not be as good.  Agree to disagree and that be that.

4. Get a Hobby

Do something else besides software development all the time.  I watch football.  This will allow you to decompress from grinding your gears doing the same thing all the time.  Switch gears and watch your productivity and attitude be on the up and up.

What Do You Think?

I ran out of things to talk about. What “soft skills” do you use at work?

Tips for the Home Coder

I don’t know about anyone else but I spend a good amount of time coding at home.  It is nice because I get to drink beer and code at the same time.  It is tough to do because I have all my home duties plus getting an hour or two to make something fun or learn somethings.  I started to look at what I do at work to save time since “Time is Money” at work but “Time is Time” at home.  Here is a quick list.

Source Control

It sounds simple enough but I looked over the times where I have blasted my code at home and spent a week restoring while a simple “svn revert” would have done the trick.  For those who are worried about standing up a new server at home, don’t.  There are many sites out there that will host your code for free.  I keep all mine at darylmathisonblog.googlecode.com.  A lot of these sites do this for open source only so if you are making the next best mousetrap, you should take the time and stand one up at your abode.  Now all your changes are in one place that can be easily backed up by someone else or yourself.

Automated Testing

Automated testing is an investment in the future.  In the beginning, it is a real pain to set up, then it becomes awesome time saver. With the click of a button tests that could have taken minutes to finish by hand are done in seconds.  Unit tests can be combined and create test suites, now any change can be tested against the whole system or just that module.  Automated test can run while you make dinner or put the kids to bed.  The other neat thing, if you walk away from a project for a while the tests can give you an idea of how that module is supposed to run so you don’t spend a week of spare time figuring out your own code.  Don’t forget to source control your automated tests too.

Use an IDE

An IDE (Integrated Development Environment) will pay back in the long run.  When I am compiling, the error log created contains links to the offending code.  When I create a new Java class, I use templates to initially set up the class.  When I am starting up a new project, the IDE organizes it to make it easy to deploy.  Good ones are expandable so I can create a tool to help me create a solution if one hasn’t been created already.  I have been using Eclipse lately and the amount of add-ons it has blows me away.  I can install servers on my computer and Eclipse will start up and shutdown the server as needed.  It automatically builds source code so I know exactly where the code doesn’t compile before I do a test.

Well, there is my quick list.  If you can think of anything else, post a comment.

Links

www.eclipse.org

www.googlecode.com

Writing Fail-Fast Code

With projects as complex as they are now, it can be hard to modify all of the code needed when a change is made.  First is to identify all the places needed for modification. The next step is to write code that handles the new requirement. The former is typically harder than the latter. Inspect the following code.

static void processIfQuiet(Data d) {

if (d.getType() == DataType.XML) {

System.out.println(“XML Data”);

}

else if (d.getType() == DataType.LEGACY) {

System.out.println(“Legacy Data”);

}

}

This code is fine if no more data types are added.  When a new DataType is created, this code could be skipped and no one would know.  The code could be pushed to production incomplete and there will be errors that the customer will find or not depending where this snippet is located.  If this is for a data loader, the new data type could be falling through and not be stored at all.  Three months down the road when the customer is generating a report relying on the new data type, the report code blows up and it takes awhile to find the error.  Here is an implementation trick that I had to learn the hard way.

static void processIfLoud(Data d) {

if (d.getType() == DataType.XML) {

System.out.println(“XML Data”);

}

else if (d.getType() == DataType.LEGACY) {

System.out.println(“Legacy Data”);

}

else { // new part

assert false: “Unknown Data Type”;

throw new RuntimeException(“Unknown Data Type”);

}

}

The else clause will catch any unknown type either throw an AssertionError or a RuntimeException depending whether or not assertions are enabled. This message could be logged and not have an ugly Error or Exception popping up. However, I would call this a “Developer’s error” meaning that it should not have got past the developer in the first place. Making it ugly will make sure it will not be missed and can be fixed before the customer gets to see it. This can be used for select statements too. See the loud version of a select statement:

import static blog.mathison.example1.DataType.XML;

import static blog.mathison.example1.DataType.LEGACY;

static void processCaseLoud(Data d) {

DataType dt = d.getType();

switch(dt) {

case XML:

System.out.println(“XML Data”);

break;

case LEGACY:

System.out.println(“Legacy Data”);

break;

default:

assert false: “Unknown Data Type”;

throw new RuntimeException(“Unknown Data Type”);

}

}

Just adding a default will make it fail where the problem is rather than three months down the road.  Do you think this not a good idea?  Are there better ways?  Leave me a comment.