黑盒测试(三)决策表分析法

发布时间:2024年01月16日

实验三: 黑盒测试——决策表分析法

【实验环境】

Windows 10 操作系统, C,C++,C#、Java或Python语言开发环境(IDE)。

【实验类型】

设计型

【实验目的】

  1. 认识黑盒测试方法中决策表分析测试方法原理
  2. 掌握黑盒测试方法中决策表分析测试方法过程

【实验内容】

【实验材料】

  1. 三角形问题

问题描述:三角形问题接受三个整数,a、b和c作为输入,用作三角形的边。程序的输出是由这三条边确定的三角形类型:等边三角形、等腰三角形、不等边三角形或非三角形。

作为输入:三角形的三条边必须满足如下条件:

C1:1<=a<=100

C2:1<=b<=100

C3:1<=c<=100

C4:a<b+c

C5:b<a+c

C6:c<a+b

  1. NextDate函数

问题描述:NextDate是一个由三个变量(月份、日期和年份)的函数。函数返回输入日期后边的那个日期。

作为输入:变量月份、日期和年都具有整数值,满足以下条件。

C1:1<=月份<=12

C2:1<=日期<=31

C3:1912<=年<=2050

【实验要求】

  1. 要求学生能够理解基于决策表的测试方法的相关概念、方法和过程。

  2. 每组二到四人,根据实验题目编写出对应的c语言或c++语言程序,组间相互交换程序,按黑盒测试的方法进行测试。

【算法描述】

本次软件测试过程当中,使用了JUnit框架,将相关的测试数据保存在csv数据文件当中,通过对csv数据文件读取测试用例来进行测试,方便我们修改测试用例,而且可以降低代码的复杂度、提高代码的可阅读性。

三角形问题程序流程:

在这里插入图片描述

NextDate问题程序流程:

在这里插入图片描述

【测试案例】

三角形问题:

决策表:

1-3233-4848-565758596061626364
C1:a<b+c?FTTTTTTTTTT
C2:b<a+c?-FTTTTTTTTT
C3:c<a+b?--FTTTTTTTT
C4:a=b?---TTTTFFFF
C5:a=c?---TTFFTTFF
C6:b=c?---TFTFTFTF
A1:非三角形
A2:不等边三角形
A3:等腰三角形
A4:等边三角形
A5:不可能

测试用例:

用例abc预期输出
DT1211非三角形
DT2241非三角形
DT3237非三角形
DT4222等边三角形
DT5不可能
DT6不可能
DT7334等腰三角形
DT8不可能
DT9343等腰三角形
DT10433等腰三角形
DT11345不等边三角形

NextData问题:

等价类划分:

M1 ={月份:每月有30天}

M2 ={月份:每月有31天,12月除外}

M3 ={月份:此月是12月}

M4 ={月份:此月是2月}

D1 ={日期:1<=日期<=27}

D2 ={日期:日期=28}

D3 ={日期:日期=29}

D4 ={日期:日期=30}

D5 ={日期:日期=31}

Y1 ={年:是闰年}

Y1 ={年:是平年}

决策表:

1-3456-91011-1415161718192021-22
C1:月份在M1M1M1M2M2M3M3M4M4M4M4M4M4
C2:日在D1,D2,D3D4D5D1,D2,D3,D4D5D1,D2,D3,D4D5D1D2D2D3D3D4,D5
C3:年在--------Y1Y2Y1Y2-
A1:不可能
A2:日期加1
A3:日期复位
A4:月加1
A5:月复位
A6:年加1

测试用例:

用例月份日期预期输出
DT120016152001/6/16
DT220016302001/7/1
DT32001631日数不合实际
DT420015152001/5/16
DT520015312001/6/1
DT6200112152001/12/16
DT7200112312002/1/1
DT820012152001/2/16
DT920042282004/2/29
DT1020012282001/3/1
DT1120042292004/3/1
DT122001229日数不合实际
DT132001230日数不合实际

【测试结果及分析】

三角形问题:

在这里插入图片描述

本次实验中由于在设计测试用例时出现了输入用例为“? ? ?”的情况,而原本的程序在读入测试用例数据时又只能识别数字类型的数据,导致三组“? ? ?”测试用例在程序首次运行时出现了报错情况。所以本次的三角形问题程序与前两次的程序相比多加了一个isNumberical方法来判断输入数据是否为数字类型,且更换了问题的程序流程图,较之先前的代码更加的全面与详细。

关于结果的分析,在本次实验中,所有输入数据中存在非数字类型的测试用例都会输出“不可能”的结果;所有不能构成三角形问题的用例都会输出“非三角形”;其余所有能够成三角形的都会被程序判断并输出其类型。

NextData问题:

在这里插入图片描述

本次实验中,NextDate问题的测试程序与之前实验中的基本一致,发生了主要变化的部分是测试用例的设计部分,明显的,本次实验的测试用例较之之前少了很多,但与之对应的是设计部分增加的工作量,即:设计部分付出的工作量与测试用例的数量两者之间大致成反比。

【实验总结】

本次实验中,可以发现两个问题在解决的过程中都采取了类似于等价类划分的方法划分了条件桩,本实验中的每个条件桩都只有true和false两种可能,但即便如此,在三角形问题中所产生的条目数量都在急剧地增加。但在第二个问题中,由于在设计时根据年月日之间存在着的一定制约关系,最终产生的条目数要少很多,可见条件项之间的制约关系有时也可以减少测试人员所编写的用例数量。

在编写代码的过程中,可以发现程序逻辑为if-else if-else的代码十分适合决策表分析法的使用,这一点在条件桩的结果只有两种情况时更为明显。其次,本实验中条件的排列顺序与规则的排列顺序对于决策表的使用都没有影响,这是极为理想的状态,适用于使用决策表。

【附-程序源码】

三角形问题源码:

import org.junit.jupiter.params.ParameterizedTest;
import org.junit.jupiter.params.provider.CsvFileSource;

import java.util.Objects;

/**
 * @author MaxBrooks chentingxian195467@163.com
 * @version 2022/10/25 19:47
 * @since JDK17
 */
class TriangleTest {
    /**
     * 判断是否是数字
     * @param a 参数a
     * @param b 参数b
     * @param c 参数c
     * @return boolean
     */
    static boolean isNumerical(String a, String b, String c){
        return !Objects.equals(a, "?") && !Objects.equals(b, "?") && !Objects.equals(c, "?");
    }

    /**
     *  判断是否输入数据是否合法,若合法,返回true,反之返回false
     * @param a 边1
     * @param b 边2
     * @param c 边3
     * @return 返回判断值
     */
    static boolean isDataUseful(Integer a, Integer b,Integer c){
        return (a >= 1 && a <= 100) && (b >= 1 && b <= 100) && (c >= 1 && c <= 100);
    }

    /**
     * 判断输入数据能否构成三角形,若能,返回true,反之返回false
     * @param a 边1
     * @param b 边2
     * @param c 边3
     * @return 返回判断值
     */
    static boolean isTriangle(Integer a, Integer b,Integer c){
        return !(a + b <= c) && !(b + c <= a) && !(a + c <= b);
    }

    /**
     * 判断三角形类型
     * @param a 边1
     * @param b 边2
     * @param c 边3
     */
    static void kindOfTriangle(Integer a, Integer b, Integer c){
        if (a.equals(b) || b.equals(c) || a.equals(c)){
            if (a.equals(b) && b.equals(c))     //没必要再添一句a.equals(c),因为前两者的可以推导出a == c的结论
                System.out.println("等边三角形");
            else
                System.out.println("等腰三角形");
        }else
            System.out.println("不等边三角形");
    }
    
    @ParameterizedTest
    @CsvFileSource(resources = "/softwarequalityandtest/DecisionTable/trianglesForDT.csv")
    void isTriangle02(String a, String b,String c){
        System.out.println("***************************");
        System.out.printf("%3s %3s %3s  ",a,b,c);
        if (isNumerical(a, b, c)){
            Integer x = Integer.valueOf(a);
            Integer y = Integer.valueOf(b);
            Integer z = Integer.valueOf(c);
            if (isDataUseful(x, y, z)){
                if (isTriangle(x, y, z)){
                    kindOfTriangle(x, y, z);
                }else
                    System.out.println("非三角形");
            }else {
                System.out.println("非三角形");
            }
        }else
            System.out.println("不可能");
    }
}

NextDate问题源码:

import org.junit.jupiter.params.ParameterizedTest;
import org.junit.jupiter.params.provider.CsvFileSource;

/**
 * @author MaxBrooks chentingxian195467@163.com
 * @version 2022/10/25 19:47
 * @since JDK17
 */
class NextDateTest {
    /**
     * 判断单个输入值是否合法:
     * 是 -> true
     * 否 -> false
     * @param yyyy  年
     * @param MM    月
     * @param dd    日
     * @return  单个输入值是否合法
     */
    static boolean isSingleInputDataUseful(Integer yyyy, Integer MM, Integer dd){
        return (yyyy >= 1912 && yyyy <= 2050) && (MM >= 1 && MM <= 12) && (dd >= 1 && dd <= 31);
    }

    /**
     * 判断是否为闰年
     * @param yyyy  年份
     * @return 若为闰年 -> true
     */
    static boolean isLeapYear(Integer yyyy){
        return (yyyy % 400 == 0) || (yyyy % 4 == 0 && yyyy % 100 != 0);
    }


    @ParameterizedTest
    @CsvFileSource(resources = "/softwarequalityandtest/DecisionTable/nextdateForDT.csv")
    void nextDate(Integer yyyy, Integer MM,Integer dd){
        if (!isSingleInputDataUseful(yyyy, MM, dd)){
            System.out.println("************************************");
            System.out.printf("当前日期为%4d/%2d/%2d  输入数据不合法\n",yyyy,MM,dd);
        }else{
            //一个标志,若为真,则说明当前月的最大日数比输入的要小,输入值有问题
            boolean dayFlag = false;
            switch (MM){
                case 1:
                case 3:
                case 5:
                case 7:
                case 8:
                case 10:
                    if (dd == 31){
                        dd = 1;
                        MM = MM + 1;
                    }else {
                        dd += 1;
                    }
                    break;
                case 4:
                case 6:
                case 9:
                case 11:
                    if (dd == 30){
                        dd = 1;
                        MM += 1;
                    } else if (dd == 31) {
                        dayFlag = true;     //输入日期超出当前月的实际最大值
                    }else
                        dd += 1;
                    break;
                case 2:
                    if (isLeapYear(yyyy)){      //闰年
                        if (dd == 29){
                            dd = 1;
                            MM = 3;
                        } else if (dd < 29) {
                            dd += 1;
                        }else
                            dayFlag = true; //输入日期超出当前月的实际最大值
                    }else {         //平年
                        if (dd == 28){
                            dd = 1;
                            MM = 3;
                        }else if (dd < 28){
                            dd += 1;
                        }else
                            dayFlag = true; //输入日期超出当前月的实际最大值
                    }
                    break;
                case 12:
                    if (dd == 31){
                        dd = 1;
                        MM = 1;
                        yyyy += 1;
                    }else {
                        dd += 1;
                    }
                    break;
                default:
            }

            if (dayFlag){
                System.out.println("************************************");
                System.out.printf("当前日期为%4d/ %2d/ %2d  日数不合实际\n",yyyy,MM,dd);
            }else {
                System.out.println("************************************");
                System.out.printf("次日日期为%4d/ %2d/ %2d  测试通过\n",yyyy,MM,dd);
            }
        }
    }
}
文章来源:https://blog.csdn.net/qq_53311714/article/details/135594061
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。