Java的分层算法如何工作?

时间:2017-04-21 14:57:57

标签: java junit

This is what I intend to do在为边界值分析设计Junit测试用例时,我遇到了问题。第一个类是基于层次结构执行逻辑排序的类。使用assertEquals时程序行为不正常。它不断重复先前的assertEquals所做的事情。因此,最终,任何进一步的评估都将被视为无用。

public class AssignCharges {
    RandomGeneratorClass rgc = new RandomGeneratorClass();

    // To test for cases less than 0
    public double getCharges(int distance, int weight) {
    // declaring the variable to be fit into the given situation
    double charges = 0;

    if(weight < 0 || distance < 0)
        throw new IllegalArgumentException("Values cannot be negative.");

    //  Testing for valid first boundary values
    //  @ <300g, <10km, RM 5
    else if(weight > 0 && weight < 300){
        charges = 5;
    }
    //  Testing for valid second boundary values @ 300-1000g
    else if(weight >= 300 && weight < 1000){
    //  @ distance < 10km, RM 8
        if(distance > 0 && distance < 10)
            charges = 8;
    //  @ 10 < distance < 30, RM 10
        else if(distance >= 10 && distance < 30)
            charges = 10;
    //  @ distance >= 30, RM 20
        else
            charges = 20;
    }
    //  Testing for valid third boundary values @ 1001-3000 g
    else if(weight >= 1000 && weight <3000){
    //  @ < 10km, RM 8
        if(distance > 0 && distance < 10)
            charges = 8;
    //  @ 10 < distance < 30, RM 12
        else if(distance >= 10 && distance < 30)
            charges = 12;
    //  @ distance > 30, RM 30
        else
            charges = 30;
    }

    //  Testing for valid fourth boundary values @ 3001-5000g
    else if(weight >= 3000 && weight < 5000){
    //  @ < 10km, RM 10
        if(distance > 0 && distance < 10)
            charges = 10;
    //  @ 10 < distance < 30, RM 15
        else if(distance >= 10 && distance < 30)
            charges = 15;
    //  @ distance > 30, RM 40
        else
            charges = 40;
    }

    //  Testing for valid fifth boundary values @ >5000g
    else if(weight >= 5000){
    //  @ < 10km, RM 15
        if(distance > 0 && distance < 10)
            charges = 15;
    //  @ 10 < distance < 30, RM 20
        else if(distance >= 10 && distance < 30)
            charges = 20;
    //  @ distance > 30, RM 50
        else
            charges = 50;
    }

    //  Testing for invalid negative boundary values
    //  The else is sufficient as the only invalid values = negative values
    else if(weight == 0 && distance == 0)
        charges = 0;

    //  replies the amount of corresponding charges
    return charges;
}

这将是Junit代码:

public class AssignChargesTest {
    @Test
    public void testAssignWeightDistanceInvalidBoundary(){
        AssignCharges ac = new AssignCharges();
        double charges;

        //  invalid boundary
        charges = ac.getCharges(0, 0);
        assertEquals(0, charges, 0);
    }

    @Test
    public void testAssignWeightDistanceFirstBoundary(){
        AssignCharges ac = new AssignCharges();
        double charges;

        //  first boundary
        charges = ac.getCharges(299, 5);
        assertEquals(5, charges, 0);
    }

    @Test
    public void testAssignWeightDistanceSecondBoundary(){
        AssignCharges ac = new AssignCharges();
        double charges;

        //  second boundary
        charges = ac.getCharges(999, 5);
        assertEquals(8, charges, 0);
        charges = ac.getCharges(999, 20);
        assertEquals(10, charges, 0);
        charges = ac.getCharges(999, 40);
        assertEquals(20, charges, 0);
    }

    @Test
    public void testAssignWeightDistanceThirdBoundary(){
        AssignCharges ac = new AssignCharges();
        double charges;

        //  third boundary
        charges = ac.getCharges(2999, 5);
        assertEquals(8, charges, 0);
        charges = ac.getCharges(2999, 20);
        assertEquals(12, charges, 0);
        charges = ac.getCharges(2999, 40);
        assertEquals(30, charges, 0);
    }

    @Test
    public void testAssignWeightDistanceFourthBoundary(){
        AssignCharges ac = new AssignCharges();
        double charges;

        //  fourth boundary
        charges = ac.getCharges(4999, 5);
        assertEquals(10, charges, 0);
        charges = ac.getCharges(4999, 20);
        assertEquals(15, charges, 0);
        charges = ac.getCharges(4999, 40);
        assertEquals(40, charges, 0);
    }

    @Test
    public void testAssignWeightDistanceFifthBoundary(){
        AssignCharges ac = new AssignCharges();
        double charges;

        //  fifth boundary
        charges = ac.getCharges(5001, 5);
        assertEquals(15, charges, 0);
        charges = ac.getCharges(5001, 20);
        assertEquals(20, charges, 0);
        charges = ac.getCharges(5001, 40);
        assertEquals(50, charges, 0);
    }


    @Test(expected = IllegalArgumentException.class)
    public void testIllegalArgumentException(){
        AssignCharges ac = new AssignCharges();
        double charges;

        //  invalid arguments list in terms of negative values:

        //  below boundary @ negative weight, negative distance
        charges = ac.getCharges(-5, -5);
        //  positive weight, negative distance
        charges = ac.getCharges(299, -5);
        charges = ac.getCharges(999, -5);
        charges = ac.getCharges(2999, -5);
        charges = ac.getCharges(4999, -5);
        charges = ac.getCharges(5001, -5);
        //  negative weight, positive distance
        charges = ac.getCharges(-1, 2);
        charges = ac.getCharges(-2, 12);
        charges = ac.getCharges(-3, 22);
        charges = ac.getCharges(-4, 32);
    }
}

1 个答案:

答案 0 :(得分:0)

JUnit只不过是Java。一旦一个Java语句突然完成(例如抛出异常),后续的语句就不会被执行。

如果你有一系列这样的陈述:

charges = ac.getCharges(-5, -5);
charges = ac.getCharges(-5, -5);
charges = ac.getCharges(-5, -5);
// ...

(我知道他们和我刚刚复制+粘贴的一样)

一旦第一个失败,其他的就是多余的。

你需要做一些事情,比如在try / catch块中包装调用,以便允许执行超出失败:

try {
  ac.getCharges(-5, -5);
  fail();
} catch (IllegalArgumentException expected) {
}
try {
  ac.getCharges(-5, -5);
  fail();
} catch (IllegalArgumentException expected) {
}
// ...

所以执行将继续。

这显然非常冗长。相反,考虑编写一个这样的方法:

void assertGetChargesFails(int a, int b) {
  try {
    ac.getCharges(a, b);
    fail();
  } catch (IllegalArgumentException expected) {
  }
}

然后调用:

assertGetChargesFails(-5, -5);
assertGetChargesFails(-5, -5);
assertGetChargesFails(-5, -5);

如果您正在使用JUnit 4.15或更高版本以及Java 8,那么assertThrows method可以更好地完成此任务:

assertThrows(IllegalArgumentException.class, () -> ac.getChanges(-5, -5));
assertThrows(IllegalArgumentException.class, () -> ac.getChanges(-5, -5));

如果未抛出异常,则每个assertThrows行都将失败。