Question
Modify the Person class from the Java Tutorial so that it is immutable, and create a JUnit test class for it called PersonTest.java. Both classes
Modify the Person class from the Java Tutorial so that it is immutable, and create a JUnit test class for it called PersonTest.java. Both classes should reside in the package "person". Your code should pass all of your unit tests, which should cover all statements and conditions in your code, and your code should pass all of the tests in Web-CAT. Your source code (but not the tests) should also meet all the Web-CAT style guidelines. You may submit your code to Web-CAT as many times as you like before the deadline.
Walkthrough of the Entire Homework
Dr. K provides a walkthrough of the entire mini-project in his videos:
A Tour of the Person Class from the Java Tutorial (1 video)
Making the Person Class Immutable (6 videos)
Unit Testing the Immutable Person Class (5 videos)
Note that Web-CAT style guidelines have been ignored in these videos. You will have to fix the style problems in your submission, including adding Javadocs to the Person class. You can do this as you follow along with the video or any time after.
Important Epilogue to the Videos
After following along in all the videos, your Person class will still have a few minor structural issues that will need to be resolved in order to pass all the Web-CAT tests:
In the areAnyNull() and areAnyInvalid() helper methods generated by Eclipse, the parameter names chosen by Eclipse are exactly the same as the names of the instance fields, which is considered a bad practice (and rejected by Web-CAT). There are two ways to fix this, with the second option being much easier than the first: Option 1 - You can refactor the parameter names to be different (such as renaming "name" to "nameX"). To do this, place the cursor within the "name" parameter of the areAnyNull() method signature, type Alt-Shift-R, and change the name of the parameter. This should change all instances (even in your Javadocs, if you've added them already) for that method. Repeat this action for each of the other parameter names within the areAnyNull() method signature, and again for all parameter names within the areAnyInvalid() method signature. Option 2 - You can reintegrate the methods you extracted during the video, placing the code back into the constructor. To do this, place the cursor within the call to areAnyNull() within the constructor, and type Alt-Shift-I (that's the letter "i") to "inline" the method and click OK. Repeat this action for the call to the areAnyInvalid() method.
The Person constructor throws NullPointerException if any parameter is null, but Web-CAT considers it a bad practice to explicitly throw this exception. It can indeed be confusing in some instances, but it's certainly not a bad practice in general. However, we need to pass the Web-CAT tests, so you must change the constructor to throw a new IllegalArgumentException instead. As a result, you will also need to update the "expect=" annotation for several of your test methods accordingly, from NullPointerException.class to IllegalArgumentException.class.
Finally, within the equals() method generated by Eclipse, the last if() statement is actually redundant, and Web-CAT will reject it as such. The code is perfectly acceptable as it is, and arguably more readable. However, we again must appease Web-CAT. To do so, you'll need to change the following two lines: if (!emailAddress.equals(other.emailAddress)) { return false; } return true into this one line instead: return emailAddress.equals(other.emailAddress); The code is now technically less redundant, but most developers would probably prefer the original form as more readable.
After making these changes, your code should still pass all the test methods in PersonTest, and you should still have 100% code coverage from EclEmma. Once you've addressed all the style issues as well, your project should receive 20/20 from Web-CAT.
PersonTest.java
package person;
import static org.junit.Assert.*; import java.io.ByteArrayOutputStream; import java.io.PrintStream; import java.time.chrono.IsoChronology; import org.junit.Before; import org.junit.Test;
@SuppressWarnings("javadoc") public class PersonTest {
private final ByteArrayOutputStream outContent = new ByteArrayOutputStream();
private Person fred; private Person jane;
@Before public void setUp() throws Exception { System.setOut(new PrintStream(outContent)); fred = new Person( "Fred", IsoChronology.INSTANCE.date(1980, 6, 20), Person.Sex.MALE, "fred@example.com"); jane = new Person( "Jane", IsoChronology.INSTANCE.date(1990, 7, 15), Person.Sex.FEMALE, "jane@example.com"); }
@Test public void testGetName() { assertEquals("Fred", fred.getName()); assertEquals("Jane", jane.getName()); }
@Test public void testGetBirthday() { assertEquals(IsoChronology.INSTANCE.date(1980, 6, 20), fred.getBirthday()); assertEquals(IsoChronology.INSTANCE.date(1990, 7, 15), jane.getBirthday()); }
@Test public void testGetGender() { assertEquals(Person.Sex.MALE, fred.getGender()); assertEquals(Person.Sex.FEMALE, jane.getGender()); }
@Test public void testGetEmail() { assertEquals("fred@example.com", fred.getEmailAddress()); assertEquals("jane@example.com", jane.getEmailAddress()); }
@Test public void testGetAge() { assertTrue(fred.getAge() >= 35); assertTrue(jane.getAge() >= 25); }
@Test public void testEnumSex() { assertEquals(Person.Sex.MALE, Person.Sex.valueOf("MALE")); assertEquals(2, Person.Sex.values().length); }
}
Person.java
import java.util.List; import java.util.ArrayList; import java.time.chrono.IsoChronology; import java.time.LocalDate; import java.time.temporal.ChronoUnit; import java.time.Period; public class Person { public enum Sex { MALE, FEMALE } String name; LocalDate birthday; Sex gender; String emailAddress; Person(String nameArg, LocalDate birthdayArg, Sex genderArg, String emailArg) { name = nameArg; birthday = birthdayArg; gender = genderArg; emailAddress = emailArg; } public int getAge() { return birthday .until(IsoChronology.INSTANCE.dateNow()) .getYears(); } public void printPerson() { System.out.println(name + ", " + this.getAge()); } public Sex getGender() { return gender; } public String getName() { return name; } public String getEmailAddress() { return emailAddress; } public LocalDate getBirthday() { return birthday; } public static int compareByAge(Person a, Person b) { return a.birthday.compareTo(b.birthday); } public static ListcreateRoster() { List roster = new ArrayList<>(); roster.add( new Person( "Fred", IsoChronology.INSTANCE.date(1980, 6, 20), Person.Sex.MALE, "fred@example.com")); roster.add( new Person( "Jane", IsoChronology.INSTANCE.date(1990, 7, 15), Person.Sex.FEMALE, "jane@example.com")); roster.add( new Person( "George", IsoChronology.INSTANCE.date(1991, 8, 13), Person.Sex.MALE, "george@example.com")); roster.add( new Person( "Bob", IsoChronology.INSTANCE.date(2000, 9, 12), Person.Sex.MALE, "bob@example.com")); return roster; } }
Step by Step Solution
There are 3 Steps involved in it
Step: 1
Get Instant Access to Expert-Tailored Solutions
See step-by-step solutions with expert insights and AI powered tools for academic success
Step: 2
Step: 3
Ace Your Homework with AI
Get the answers you need in no time with our AI-driven, step-by-step assistance
Get Started