当我在Haskell中运行测试时,我的输出将显示为_

时间:2012-12-03 14:03:14

标签: haskell

好的,所以我设置了多个测试用例,然后将它们组合在一起。 我忘记了一些代码,所以我添加了

问题是,当我举例如 Main> tests 1 时,会显示正确答案,但如果我尝试单独运行测试用例,例如 main> test0 my输出变为“TestCase _”

main> Alltests 我的输出是“TestList [TestLabel test1 TestCase _,TestLabel test0 TestCase _,TestLabel test7 TestCase _,TestLabel test51 TestCase _]”

我的问题是导致_的原因以及为什么不识别测试用例

assertException :: (Exception e, Eq e) => e -> IO a -> IO ()
assertException ex action =
      handleJust isWanted (const $ return ()) $ do
            action
            assertFailure $ "Expected exception: " ++ show ex
     where isWanted = guard . (== ex) 

assertError ex f = 
      assertException (ErrorCall ex) $ evaluate f



tests :: Integer -> [Integer]

tests n | n == 0              = error "Not positive"
        | n == 1              = [1]
        | (n `div` 2 == 0)    = n:tests(n*2)
        | otherwise           = n:tests(3*n) 



test0 = 
      TestCase ( assertError
                    "tests 0" 
                     ( tests 0 )
               )


test7 = 
      TestCase ( assertEqual
                    "tests 7" 
                [7,18,9]
                     ( tests 7 )
                )

test51 = 
      TestCase ( assertEqual
                    [9,8,9]
                    "tests 51"

                  ( tests 51 )
               )



alltests = 
     TestList [
             -- TestLabel "test1" test1
               TestLabel "test0" test0
             , TestLabel "test7" test7
             , TestLabel "test51"test51
             ]

2 个答案:

答案 0 :(得分:5)

当您在提示符下键入test0allTests(注意:不能以大写字母开头,因为它不是构造函数)时,您实际上并不运行测试。 test0也是类型TestallTests的值。因此,当您在ghci提示符下键入其中任何一个时,该值将通过String转换为show,然后打印出String

TestShow个实例无法将包含的Assertion转换为有意义的String,因为AssertionIO - 动作。因此,它一般在那里显示一个下划线,表示“这是一个断言”。

tests 1
另一方面,

tests 1 :: Integral a => [a]类型的表达式,当您在提示符下键入此类表达式时,通过String将其转换为show(在修复之后)通过默认为a)来键入变量Integer,但此处Show实例要求对列表进行完全评估。

要实际运行测试,您需要runTestTTperformTest(或来自HUnit的其他测试运行者之一)。

答案 1 :(得分:1)

起初我不得不说你的代码很乱。你确实写过,复制破坏了你的格式,但是,如果你真的想要一个写得很好的问题的解决方案,那么写一个写得很好的问题也会很好。 然而,实际运行代码需要进行一些更改。

例如: 在您对test0的定义中,您使用了一个名为assertError的函数,该函数不存在,因此我假设您在其他测试用例中表示assertEqual。测试用例的另一个问题是函数assertEqual :: (Eq a, Show a) => String -> a -> a -> Assertion用法:它需要三个参数,但在你的定义中它只有两个。后两个参数代表预期值和实际值,我猜你忘记了实际值。所以我不知道,你想测试什么。

编辑:但我想您的函数和相应测试的问题是,您的函数构造了一个无限列表(01除外作为n的输入值) ,因此您的函数不会像测试用例一样终止。 (我首先认为这也是产生神秘输出的原因,但这似乎是错误的。)