分割版本字符串直到找到为止

huangapple go评论114阅读模式
英文:

splitting version string until found

问题

在这个问题中,你想要实现以下输出:

  1. Version 3.14.15.5.123.2 is called: apple
  2. Version 3.14.15.13.123 is called: orange
  3. Version 3.14.15.19.12 is called: pear

你在考虑使用字符串搜索、切片、搜索、切片循环的方式来找到匹配的结果。你想知道是否有更简单的方法。

以下是一个可能的解决方案:

  1. package main
  2. import (
  3. "fmt"
  4. )
  5. type apps []app
  6. type app struct {
  7. version string
  8. }
  9. type releases []release
  10. type release struct {
  11. name string
  12. platform string
  13. }
  14. func main() {
  15. var versions releases
  16. versions = append(versions, release{name: "apple", platform: "3.14.15"})
  17. versions = append(versions, release{name: "orange", platform: "3.14.15.13"})
  18. versions = append(versions, release{name: "pear", platform: "3.14.19"})
  19. var test apps
  20. test = append(test, app{version: "3.14.15.5.123.2"}) // should map to apple
  21. test = append(test, app{version: "3.14.15.13.123"}) // should map to orange
  22. test = append(test, app{version: "3.14.15.19.12"}) // should map to pear
  23. for _, r := range test {
  24. for _, v := range versions {
  25. if v.platform == r.version {
  26. fmt.Printf("Version %s is called: %s\n", r.version, v.name)
  27. break
  28. }
  29. }
  30. }
  31. }

这段代码使用了两个结构体类型:appreleaseapp 结构体表示应用程序的版本,release 结构体表示发布的版本。我们首先定义了一个 versions 切片,其中包含了所有的发布版本。然后,我们定义了一个 test 切片,其中包含了要测试的应用程序版本。

接下来,我们使用嵌套的循环来比较每个测试版本和发布版本,如果找到匹配的版本,就输出对应的应用程序名称。

希望这可以帮助到你!

英文:

Sort of went down the rabbit hole on this one:

  1. package main
  2. import (
  3. "fmt"
  4. )
  5. type apps []app
  6. type app struct {
  7. version string
  8. }
  9. type releases []release
  10. type release struct {
  11. name string
  12. platform string
  13. }
  14. func main() {
  15. var versions releases
  16. versions = append(versions, release{name: "apple", platform: "3.14.15"})
  17. versions = append(versions, release{name: "orange", platform: "3.14.15.13"})
  18. versions = append(versions, release{name: "pear", platform: "3.14.19"})
  19. var test apps
  20. test = append(test, app{version: "3.14.15.5.123.2"}) // should map to apple
  21. test = append(test, app{version: "3.14.15.13.123"}) // should map to orange
  22. test = append(test, app{version: "3.14.15.19.12"}) // should map to pear
  23. for _, r := range test {
  24. fmt.Printf("Version %s is called: %s\n", r.version, "?")
  25. }
  26. }

I'm trying to achieve the following output:

  1. Version 3.14.15.5.123.2 is called: apple
  2. Version 3.14.15.13.123 is called: orange
  3. Version 3.14.15.19.12 is called: pear

I was thinking some sort of string search, slice, search, slice loop until i could find a match? is there an easier way?

答案1

得分: 3

你需要找到发布类型中最长的前缀。为此,你可以实现一个类似下面这样的函数:

  1. package main
  2. import (
  3. "fmt"
  4. "strings"
  5. )
  6. type apps []app
  7. type app struct {
  8. version string
  9. }
  10. type releases []release
  11. type release struct {
  12. name string
  13. platform string
  14. }
  15. func (r releases) FindName(version string) string {
  16. result := ""
  17. max := 0
  18. for _, release := range r {
  19. if strings.HasPrefix(version, release.platform) {
  20. if max < len(release.platform) {
  21. max = len(release.platform)
  22. result = release.name
  23. }
  24. }
  25. }
  26. return result
  27. }
  28. func main() {
  29. var versions releases
  30. versions = append(versions, release{name: "apple", platform: "3.14.15"})
  31. versions = append(versions, release{name: "orange", platform: "3.14.15.13"})
  32. versions = append(versions, release{name: "pear", platform: "3.14.19"})
  33. var test apps
  34. test = append(test, app{version: "3.14.15.5.123.2"}) // 应该映射到 apple
  35. test = append(test, app{version: "3.14.15.13.123"}) // 应该映射到 orange
  36. test = append(test, app{version: "3.14.19.12"}) // 应该映射到 pear
  37. for _, r := range test {
  38. fmt.Printf("版本 %s 被称为:%s\n", r.version, versions.FindName(r.version))
  39. }
  40. }
英文:

You have to find the longest prefix in the releases type. For this you can implement a func like this one:

  1. package main
  2. import (
  3. &quot;fmt&quot;
  4. &quot;strings&quot;
  5. )
  6. type apps []app
  7. type app struct {
  8. version string
  9. }
  10. type releases []release
  11. type release struct {
  12. name string
  13. platform string
  14. }
  15. func (r releases) FindName(version string) string {
  16. result := &quot;&quot;
  17. max := 0
  18. for _, release := range r {
  19. if strings.HasPrefix(version, release.platform) {
  20. if max &lt; len(release.platform) {
  21. max = len(release.platform)
  22. result = release.name
  23. }
  24. }
  25. }
  26. return result
  27. }
  28. func main() {
  29. var versions releases
  30. versions = append(versions, release{name: &quot;apple&quot;, platform: &quot;3.14.15&quot;})
  31. versions = append(versions, release{name: &quot;orange&quot;, platform: &quot;3.14.15.13&quot;})
  32. versions = append(versions, release{name: &quot;pear&quot;, platform: &quot;3.14.19&quot;})
  33. var test apps
  34. test = append(test, app{version: &quot;3.14.15.5.123.2&quot;}) // should map to apple
  35. test = append(test, app{version: &quot;3.14.15.13.123&quot;}) // should map to orange
  36. test = append(test, app{version: &quot;3.14.19.12&quot;}) // should map to pear
  37. for _, r := range test {
  38. fmt.Printf(&quot;Version %s is called: %s\n&quot;, r.version, versions.FindName(r.version))
  39. }
  40. }

答案2

得分: 1

如果你需要进行多次查找,那么你可以构建一个索引并在其中进行搜索。这样,搜索的最大时间复杂度将是 O(n),其中 n 是你要搜索的版本号的长度。

  1. package main
  2. import (
  3. "fmt"
  4. "sort"
  5. "strings"
  6. )
  7. type apps []app
  8. type app struct {
  9. version string
  10. }
  11. type releases []release
  12. type release struct {
  13. name string
  14. platform string
  15. }
  16. var index map[string]string
  17. func BuildIndex(r releases) {
  18. sort.Slice(r, func(i, j int) bool { return r[i].platform < r[j].platform })
  19. index = make(map[string]string)
  20. for _, release := range r {
  21. s := ""
  22. for _, rn := range release.platform {
  23. s += string(rn)
  24. if strings.HasSuffix(s, ".") {
  25. continue
  26. }
  27. if _, found := index[s]; !found {
  28. index[s] = release.name
  29. }
  30. }
  31. }
  32. }
  33. func FindInIndex(v string) string {
  34. for {
  35. if name, found := index[v]; found {
  36. return name
  37. }
  38. v = v[:len(v)-1]
  39. if v == "" {
  40. break
  41. }
  42. }
  43. return ""
  44. }
  45. func main() {
  46. var versions releases
  47. versions = append(versions, release{name: "apple", platform: "3.14.15"})
  48. versions = append(versions, release{name: "orange", platform: "3.14.15.13"})
  49. versions = append(versions, release{name: "pear", platform: "3.14.19"})
  50. BuildIndex(versions)
  51. var test apps
  52. test = append(test, app{version: "3.14.15.5.123.2"}) // should map to apple
  53. test = append(test, app{version: "3.14.15.13.123"}) // should map to orange
  54. test = append(test, app{version: "3.14.19.12"}) // should map to pear
  55. for _, r := range test {
  56. fmt.Printf("Version %s is called: %s\n", r.version, FindInIndex(r.version))
  57. }
  58. }

以上是要翻译的代码部分。

英文:

If you need to make so many lookups, then you can build an index and search in it. This way a search would take optimally maximum O(n) where n is the length of the version you are searching.

  1. package main
  2. import (
  3. &quot;fmt&quot;
  4. &quot;sort&quot;
  5. &quot;strings&quot;
  6. )
  7. type apps []app
  8. type app struct {
  9. version string
  10. }
  11. type releases []release
  12. type release struct {
  13. name string
  14. platform string
  15. }
  16. var index map[string]string
  17. func BuildIndex(r releases) {
  18. sort.Slice(r, func(i, j int) bool { return r[i].platform &lt; r[j].platform })
  19. index = make(map[string]string)
  20. for _, release := range r {
  21. s := &quot;&quot;
  22. for _, rn := range release.platform {
  23. s += string(rn)
  24. if strings.HasSuffix(s, &quot;.&quot;) {
  25. continue
  26. }
  27. if _, found := index
    展开收缩
    ; !found {
  28. index
    展开收缩
    = release.name
  29. }
  30. }
  31. }
  32. }
  33. func FindInIndex(v string) string {
  34. for {
  35. if name, found := index[v]; found {
  36. return name
  37. }
  38. v = v[:len(v)-1]
  39. if v == &quot;&quot; {
  40. break
  41. }
  42. }
  43. return &quot;&quot;
  44. }
  45. func main() {
  46. var versions releases
  47. versions = append(versions, release{name: &quot;apple&quot;, platform: &quot;3.14.15&quot;})
  48. versions = append(versions, release{name: &quot;orange&quot;, platform: &quot;3.14.15.13&quot;})
  49. versions = append(versions, release{name: &quot;pear&quot;, platform: &quot;3.14.19&quot;})
  50. BuildIndex(versions)
  51. var test apps
  52. test = append(test, app{version: &quot;3.14.15.5.123.2&quot;}) // should map to apple
  53. test = append(test, app{version: &quot;3.14.15.13.123&quot;}) // should map to orange
  54. test = append(test, app{version: &quot;3.14.19.12&quot;}) // should map to pear
  55. for _, r := range test {
  56. fmt.Printf(&quot;Version %s is called: %s\n&quot;, r.version, FindInIndex(r.version))
  57. }
  58. }

huangapple
  • 本文由 发表于 2021年9月3日 04:06:26
  • 转载请务必保留本文链接:https://go.coder-hub.com/69036439.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定