Reputation: 8067
I am new to testing. I am using netbeans.
I have college assignment for junit testing but i am not so sure how should i test random number method. My question is how should I test below method?
/**
* Method will generate a set of integers between the minimum and maximum of
* the requested size. If the uniqueElements is true the set will consist of
* unique integer values
*
* @param size the number of elements for the array
* @param minimum the lower value of the range of integers to generate
* @param maximum the upper value of the range of integers to generate
* @param uniqueElements flag for unique values
* @return
*/
public static ArrayList<Integer> createSet(int size, int minimum, int maximum, boolean uniqueElements) {
boolean filled = false;
int i = 0;
ArrayList<Integer> arraySet = null;
if (size > 0) {
arraySet = new ArrayList<Integer>();
boolean isUnique = false;
while (!filled) {
int randi = (int) (Math.random() * (maximum - minimum)) + minimum;
// C isu = true;
// C for (int j = 0; j < i && u; j++) {
// ** NEED &= isu = randi != A.get(j);
// C }
//
// if (isu || !u) {
// A.add(randi);
// i++;
// }
isUnique = true;
for (int j = 0; j < i && uniqueElements; j++) {
isUnique = randi != arraySet.get(j);
}
if (isUnique || !uniqueElements) {
arraySet.add(randi);
i++;
}
filled = (i == size);
}
}
return arraySet;
}
For this assignment professor told me that cover 100% code coverage. I am not sure how should i Do that?
I created this test case
/**
* Test of createSet method, of class ArraySetUtilities.
*/
@Test(timeout = 5000)
public void testCreateSet() {
System.out.println("createSet");
int size = 0;
int minimum = 0;
int maximum = 0;
boolean uniqueElements = true;
ArrayList<Integer> expResult = null;
ArrayList<Integer> result = ArraySetUtilities.createSet(size, minimum, maximum, uniqueElements);
assertEquals(expResult, result);
}
Thank you in advance
Upvotes: 0
Views: 894
Reputation: 1040
As @flopshot said, you should have all the IFs cover. In order to do that you have to control the random number that your test is producing.
In order to do so I would recommend you would replace the Math.random() with SingletonRandom and use mock framework such as JMockit.
Changing your "production" code in order to be testable is something that has to be considered carefully, however, mocking random is good scenario for this.
You can create interface with random method and implement it twice stack exchange question, or create a class SingletonRandom and Mock it in your test. The same concept is described here mock singleton with jmockit.
public class SingletonRandom {
private SingletonRandom() {}
public static SingletonRandom newInstance() {
return new SingletonRandom();
}
public double getRandomNumber() {
return Math.random();
}
}
In your class do something like that
int randi = (int) (SingletonRandom.newInstance().random() * (maximum - minimum)) + minimum;
And in the test Mock the SingletonRandom
ClassTest {
@Mocked
SingletonRandom SingletonRandom;
@Test
testMethod() {
new Expectations() {{
SingletonGenerator.newInstance(); result = singletonGenerator;
singletonGenerator.getRandomNumber(); result = new double[] { 1.2, 2.5, 3.7 }; // Add the requested "random" numbers for your if casses
}};
// Add calls to method with assertion here
}
}
You can further read about Expectations here A Guide to JMockit Expectations
Upvotes: 1