Arpit Patel
Arpit Patel

Reputation: 8067

Junit testing with random number

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

Answers (1)

Gal S
Gal S

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

Related Questions