测试具有相同内容的 Go 中 map 的等价性,但测试失败

标签 testing map go equivalence

这是 Go 中的一个字数统计函数

package wc

import (
    "regexp"
    "strings"
)

type Histogram map[string]int

func WordCount(input string) Histogram {
    histogram := make(map[string]int)
    re := regexp.MustCompile("[^a-zA-Z0-9 ]*")
    input = re.ReplaceAllString(input, "")

    for _, word := range strings.Split(input, " ") {
        if word == "" {
            continue
        }
        histogram[strings.ToLower(word)]++
    }

    return histogram
}

此代码不确定地通过或未通过测试。有时由于预期 map 与实际 map 不匹配而失败。但是,两者的内容完全相同。我认为 map 比较存在一些问题。我不知道该如何解决。请有人帮助我!

这是测试套件代码

package wc

import (
    "fmt"
    "testing"
)

var testCases = []struct {
    description string
    input       string
    output      Histogram
}{
    {
        description: "a single word",
        input:       "word",
        output:      Histogram{"word": 1},
    },
    {
        description: "one of each",
        input:       "one of each",
        output:      Histogram{"one": 1, "of": 1, "each": 1},
    },
    {
        description: "multiple occurrences",
        input:       "one fish two fish red fish blue fish",
        output:      Histogram{"one": 1, "fish": 4, "two": 1, "red": 1, "blue": 1},
    },
    {
        description: "ignore punctuation",
        input:       "car : carpet as java : javascript!!&@$%^&",
        output:      Histogram{"car": 1, "carpet": 1, "as": 1, "java": 1, "javascript": 1},
    },
    {
        description: "including numbers",
        input:       "testing, 1, 2 testing",
        output:      Histogram{"testing": 2, "1": 1, "2": 1},
    },
    {
        description: "normalises case",
        input:       "go Go GO",
        output:      Histogram{"go": 3},
    },
}

func TestWordCount(t *testing.T) {
    for _, tt := range testCases {
        expected := fmt.Sprintf("%v", tt.output)
        actual := fmt.Sprintf("%v", WordCount(tt.input))

        if expected != actual {
            t.Fatalf("%s\n\tExpected: %v\n\tGot: %v", tt.description, expected, actual)
        } else {
            t.Logf("PASS: %s - WordCount(%s)", tt.description, tt.input)
        }
    }
}

以下是失败情况的示例:

1.
Expected: map[two:1 red:1 blue:1 one:1 fish:4]
Got: map[one:1 fish:4 two:1 red:1 blue:1]
2.
Expected: map[one:1 fish:4 two:1 red:1 blue:1]
Got: map[red:1 blue:1 one:1 fish:4 two:1]
3.
Expected: map[java:1 javascript:1 car:1 carpet:1 as:1]
Got: map[javascript:1 car:1 carpet:1 as:1 java:1]
...

更多信息在这里: http://exercism.io/submissions/cf94f4732fd97335be2e755f

最佳答案

您不能将expectedactual!= 进行比较,因为它比较的是 map 的字符串表示形式,所以它会起作用仅随机(如果值以相同顺序打印)。

您需要做的是使用reflectDeepEqual() 方法来比较 map :

import "reflect"
// ...

if !reflect.DeepEqual(tt.output, WordCount(tt.input)) {
// ...

它将首先检查两个映射是否为nil,然后检查它们是否具有相同的长度,然后检查它们是否具有相同的一组(键,值)对。

关于测试具有相同内容的 Go 中 map 的等价性,但测试失败,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21745073/

相关文章:

map[Task]int64 其中 Task 是一个接口(interface)

angularjs - 将数据传递到指令进行测试时的 Angular 指令单元测试问题

java - 如何将 JUnit 测试用例导出到可执行文件 .jar 中?

typescript - NestJS - 测试套件无法运行从 'src/article/article.entity' 找不到模块 'comment/comment.entity.ts'

dynamic - Solrj 和动态字段

java - 将 LinkedHashMap 中的所有键提取到列表中的方法

xml - 如何从在线 xml 文件中解码 xml 数据

json - 我的结构没有编码为 json

go - 如何将字节的 ASCII 值添加到 golang 中的整数?

testing - 仅在运行测试时生成调试输出