简体   繁体   English

在 Python 3 中使用库“unittest”进行单元测试

[英]Unit testing using library 'unittest' in Python 3

I need to write test cases using unit test in Python for testing circle creation.我需要在 Python 中使用单元测试编写测试用例来测试圈子的创建。

Define a class Circle with method init which initializes a circle with attribute radius, having following restrictions.使用方法 init 定义一个 class Circle,它初始化一个具有属性 radius 的圆,具有以下限制。

  1. radius must be numeric value, if not raise type error with error message "radius must be number".半径必须是数值,如果不是引发类型错误,错误消息为“半径必须是数字”。
  2. radius must be between 0 to 1000 inclusive on both sides, if not raise the value error with error message "radius must be between 0 and 1000 inclusive"两侧的半径必须在 0 到 1000 之间(含),如果不引发错误消息“半径必须在 0 到 1000(含)之间”的值错误
  3. Define a class method area and circumference which must return values rounded off to 2 decimals.定义一个 class 方法 area and circumference ,它必须返回四舍五入到两位小数的值。

Complete the definition of class TestingCircleCircumference which tests the behaviour of circumference method as specification below.完成 class TestingCircleCircumference 的定义,它测试圆周方法的行为,如下所述。

Define the test method test_circlecircum_with_random_numerical_radius which creates circle c1 with radius 2.5 and check if its computed circumference match the value 15.71定义测试方法 test_circlecircum_with_random_numerical_radius 创建半径为 2.5 的圆 c1 并检查其计算的周长是否与值 15.71 匹配

Define the test method test_circlecircum_with__min_radius which creates circle c2 with radius 0 and check if its computed circumference match the value 0定义测试方法 test_circlecircum_with__min_radius 创建半径为 0 的圆 c2 并检查其计算的周长是否与值 0 匹配

Define the test method test_circlecircum_with_max_radius which creates circle c3 with radius 1000 and check if its computed circumference match the value 6283.19定义测试方法 test_circlecircum_with_max_radius,它创建半径为 1000 的圆 c3,并检查其计算的周长是否与值 6283.19 匹配

My code is:我的代码是:

import inspect
import re
import unittest
import math

class Circle:

    def __init__(self, radius):

        try:
            if not isinstance(radius, (int, float)):
                raise TypeError
            elif 1000 >= radius >= 0:
                self.radius=radius
            else:
                raise ValueError
        except ValueError:
            raise ValueError("radius must be between 0 and 1000 inclusive")
        except TypeError:
            raise TypeError("radius must be a number")

def area(self):

    y = math.pi*(self.radius**2)
    return round(y, 2)

def circumference(self):

    x = math.pi*2*self.radius
    return round(x, 2)

class TestCircleArea(unittest.TestCase):

    def test_circlearea_with_random_numeric_radius(self):

        c1 = Circle(2.5)
        self.assertEqual(c1.area(), 19.63)


    def test_circlearea_with_min_radius(self):

        c2 = Circle(0)
        self.assertEqual(c2.area(), 0)

    def test_circlearea_with_max_radius(self):

        c3 = Circle(1000.1)
        self.assertEqual(c3.area(), 3141592.65)

The below code is generated by the system and I can't edit it.下面的代码是系统生成的,我无法编辑。 This code is from HackerRank .此代码来自HackerRank

if __name__ == '__main__':

    fptr = open('output.txt', 'w')

    runner = unittest.TextTestRunner(fptr)

    unittest.main(testRunner=runner, exit=False)

    fptr.close()

    with open('output.txt') as fp:
        output_lines = fp.readlines()


    pass_count = [len(re.findall(r'\.', line)) for line in output_lines if line.startswith('.')
                     and line.endswith('.\n')]

    pass_count = pass_count[0]

    print(str(pass_count))

    doc1 = inspect.getsource(TestCircleArea.test_circlearea_with_random_numeric_radius)
    doc2 = inspect.getsource(TestCircleArea.test_circlearea_with_min_radius)
    doc3 = inspect.getsource(TestCircleArea.test_circlearea_with_max_radius)

    assert1_count = len(re.findall(r'assertEqual', doc1))

    print(str(assert1_count))

    assert1_count = len(re.findall(r'assertEqual', doc2))

    print(str(assert1_count))

    assert1_count = len(re.findall(r'assertEqual', doc3))

    print(str(assert1_count))

The error I am getting is:我得到的错误是:

Traceback (most recent call last):
  File "main.py", line 75, in <module>
    pass_count = pass_count[0]
IndexError: list index out of range

I was able to solve the given problem using the below class and testing class methods .我能够使用下面的类和测试类方法解决给定的问题。

class Circle:
    
    def __init__(self, radius):
        # Define the initialization method below
        self.radius = radius
        if not isinstance(self.radius, (int, float)):
            raise TypeError("radius must be a number")
        elif self.radius < 0 or self.radius > 1000:
            raise ValueError("radius must be between 0 and 1000 inclusive")
        else:
            pass
        
    def area(self):
        # Define the area functionality below
        return round(math.pi*(self.radius**2), 2)
               
    def circumference(self):
        # Define the circumference functionality below
        return round(2*math.pi*self.radius, 2)
        
class TestCircleCircumference(unittest.TestCase):
    
    def test_circlecircum_with_random_numeric_radius(self):
        # Define a circle 'c1' with radius 2.5 and check if 
        # its circumference is 15.71
        c1 = Circle(2.5)
        self.assertEqual(c1.circumference(), 15.71)

        
    def test_circlecircum_with_min_radius(self):
        # Define a circle 'c2' with radius 0 and check if 
        # it's circumference is 0.
        c2 = Circle(0)
        self.assertEqual(c2.circumference(),0)
                
    def test_circlecircum_with_max_radius(self):
        # Define a circle 'c3' with radius 1000 and check if 
        # it's circumference is 6283.19.
        c3 = Circle(1000)
        self.assertEqual(c3.circumference(),6283.19)

Just modify the code as follows:只需修改代码如下:

  1. Remove/delete the passcount line移除/删除 passcount 行
  2. Directly assign the value ie total number of tests to be performed.直接分配值,即要执行的测试总数。
  3. Enjoy, no more errors.享受,没有更多的错误。

This is just to skip the default thing which keeps irritating.这只是为了跳过不断令人恼火的默认事情。

You getting the error because the value of c3 is not getting initialized due to the conditions you are putting in your __init__ method.您收到错误是因为c3的值由于您在__init__方法中放置的条件而未初始化。

Please remove it if you want to initialize it to 1000.1:如果要将其初始化为 1000.1,请将其删除:

class Circle:
    
    def __init__(self, radius):
        self.radius = radius

    def area(self):
        return round((math.pi*(self.radius)**2), 2)
        
               
    def circumference(self):
        return round((math.pi*(self.radius)*2), 2)

One more thing: the area of c3 is 3142221.0, not the value you are testing.还有一件事:c3的面积是3142221.0,不是你测试的值。 Please print and check it once.请打印并检查一次。

class TestCircleArea(unittest.TestCase):
    
    def test_circlearea_with_random_numeric_radius(self):
        c1 = Circle(2.5)
        self.assertEqual(c1.area(), 19.63)
        
    def test_circlearea_with_min_radius(self):
        c2 = Circle(0)
        self.assertEqual(c2.area(), 0.0)

    def test_circlearea_with_max_radius(self):
        c3 = Circle(1000.1)
        #print(c3.area())
        self.assertEqual(c3.area(), 3142221.0)
def test_circlearea_with_max_radius(self):
    c3 = Circle(1000)
    #print(c3.area())
    self.assertEqual(c3.area(), 3141592.65)

I verified this works fine.我验证这工作正常。 The number is 1000, not 1000.1.数字是 1000,而不是 1000.1。 It seems like issue with input suggestion.输入建议似乎有问题。

class Circle:班级圈:

def __init__(self, radius):
  
    self.radius = 0
    if not isinstance(radius,(int,float)):
        raise TypeError("radius must be a number")
    elif radius < 0 or radius > 1000:
        raise ValueError("radius must be between 0 and 1000 inclusive")
    else:
        self.radius = radius
    
def area(self):
    
    return round(math.pi*(self.radius**2),2) 
           
def circumference(self):
 
    return round((math.pi*self.radius*2),2)

    

class TestCircleArea(unittest.TestCase):类 TestCircleArea(unittest.TestCase):

def test_circlearea_with_random_numeric_radius(self):
    
    c1 = Circle(2.5)
    self.assertEqual(c1.area(), 19.63)
    
def test_circlearea_with_min_radius(self):
    
    c2 = Circle(0)
    self.assertEqual(c2.area(), 0)
    
def test_circlearea_with_max_radius(self):
    
    c3 = Circle(1000)
    self.assertEqual(c3.area(), 3141592.65)

You can refer to this GitHub file可以参考这个GitHub文件

or或者

# Define below the class 'Circle' and it's methods.
class Circle:
    
    def __init__(self, radius):
        # Define the initialization method below
        pattern = re.compile("^\\-?[0-9]")
        if(pattern.match(str(radius))):
            if(radius >= 0 and radius <= 1000):
                self.radius = radius
            else:
                raise ValueError("radius must be between 0 and 1000 inclusive")
        else:
            raise TypeError("radius must be a number")
        
        
    def area(self):
        # Define the area functionality below
        return round(((self.radius ** 2) * math.pi),2)

    def circumference(self):
        # Define the circumference functionality below
        return round((self.radius * 2 * math.pi),2)
        
class TestCircleCircumference(unittest.TestCase):
    
    def test_circlecircum_with_random_numeric_radius(self):
        # Define a circle 'c1' with radius 2.5 and check if 
        # it's circumference is 15.71
        c1= Circle(2.5)
        self.assertEqual(c1.circumference(), 15.71)
        
    def test_circlecircum_with_min_radius(self):
        # Define a circle 'c2' with radius 0 and check if 
        # it's circumference is 0.
        c2= Circle(0)
        self.assertEqual(c2.circumference(), 0)
        
    def test_circlecircum_with_max_radius(self):
        # Define a circle 'c3' with radius 1000 and check if 
        # it's circumference is 6283.19.
        c3= Circle(1000)
        self.assertEqual(c3.circumference(), 6283.19)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM