查找、解析和验证电子邮件地址

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

finding, parsing and validating email addresses

问题

  1. import "fmt"
  2. func main() {
  3. email := "learning@gmail.com"
  4. atTrue := false
  5. s := ""
  6. domain := ""
  7. tld := ""
  8. for i := 0; i < len(email); i++ {
  9. if atTrue {
  10. s += string(email[i])
  11. }
  12. if string(email[i]) == "@" {
  13. atTrue = true
  14. }
  15. if string(email[i]) == "." {
  16. atTrue = false
  17. domain = s
  18. s = ""
  19. }
  20. }
  21. tld = s
  22. fmt.Println("Domain:", domain, "and TLD:", tld)
  23. }

当前输出:Domain: gmail and TLD: com

期望输出:Domain: gmail and TLD: com

如何指示从某个字符串到某个字符串的循环?

英文:
  1. import &quot;fmt&quot;
  2. func main() {
  3. email := &quot;learning@gmail.com&quot;
  4. atTrue := false
  5. s := &quot;&quot;
  6. for i := 0; i &lt; len(email); i++ {
  7. if atTrue {
  8. s += string(email[i])
  9. }
  10. if string(email[i]) == &quot;@&quot; {
  11. atTrue = true
  12. }
  13. }
  14. fmt.Println(s)
  15. }

current output: gmail.com

expect output: Domain: gmail and TLD: com

How to indicate looping from certain string to certain string?

答案1

得分: 3

使用strings.Split函数

  1. email := "learning@gmail.com"
  2. split := strings.Split(email, "@")
  3. split = strings.Split(split[1], ".")
  4. fmt.Println("Domain:", split[0])
  5. fmt.Println("TLD:", split[1])

你可以使用mail.ParseAddress函数验证电子邮件字符串

  1. email := "learning@gmail.com"
  2. addr, err := mail.ParseAddress(email)
  3. if err != nil {
  4. log.Fatal(err)
  5. }

如果TLD是co.id,输出仍然是co.id吗?
尝试找到.的第一个索引(strings.Index),并使用它来分隔字符串

  1. email := "learning@gmail.co.id"
  2. split := strings.Split(email, "@")
  3. index := strings.Index(split[1], ".")
  4. fmt.Println("Domain:", split[1][:index])
  5. fmt.Println("TLD:", split[1][index+1:])

或者使用regexp.Split函数

  1. email := "learning@gmail.co.id"
  2. split := strings.Split(email, "@")
  3. split = regexp.MustCompile("[.]").
  4. Split(split[1], 2)
  5. fmt.Println("Domain:", split[0])
  6. fmt.Println("TLD:", split[1])

或者使用strings.SplitN

  1. email := "learning@gmail.co.id"
  2. split := strings.Split(email, "@")
  3. split = strings.SplitN(split[1], ".", 2)
  4. fmt.Println("Domain:", split[0])
  5. fmt.Println("TLD:", split[1])

或者使用strings.Cut

  1. _, host, found := strings.Cut(email, "@")
  2. if !found {
  3. t.Fatal("fail cut to host (Domain + TLD)")
  4. }
  5. domain, tld, found := strings.Cut(host, ".")
  6. if !found {
  7. t.Fatal("fail cut to Domain and TLD")
  8. }
  9. fmt.Println("Domain:", domain)
  10. fmt.Println("TLD:", tld)

PLAYGROUND

基准测试

  1. const (
  2. quantity = 10000
  3. userLength = 10
  4. domain = "gmail.com"
  5. )
  6. var (
  7. letterRunes = []rune("abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ")
  8. emails = make([]string, 0, quantity)
  9. seeded = rand.New(rand.NewSource(time.Now().UnixMilli()))
  10. )
  11. for i := 0; i < quantity; i++ {
  12. user := make([]rune, userLength)
  13. for i := range user {
  14. user[i] = letterRunes[seeded.Intn(len(letterRunes))]
  15. }
  16. emails = append(emails, fmt.Sprintf("%s@%s", string(user), domain))
  17. }
  18. b.Run("strings.Split", func(b *testing.B) {
  19. b.ReportAllocs()
  20. b.ResetTimer()
  21. var domain, tld string
  22. for i := 0; i < b.N; i++ {
  23. for _, email := range emails {
  24. domain, tld = stringsSplit(email)
  25. }
  26. }
  27. _, _ = domain, tld
  28. })
  29. b.Run("strings.SplitN", func(b *testing.B) {
  30. b.ReportAllocs()
  31. b.ResetTimer()
  32. var domain, tld string
  33. for i := 0; i < b.N; i++ {
  34. for _, email := range emails {
  35. domain, tld = stringsSplitN(email)
  36. }
  37. }
  38. _, _ = domain, tld
  39. })
  40. b.Run("strings.Index+strings.Split", func(b *testing.B) {
  41. b.ReportAllocs()
  42. b.ResetTimer()
  43. var domain, tld string
  44. for i := 0; i < b.N; i++ {
  45. for _, email := range emails {
  46. domain, tld = stringsIndexAndStringsSplit(email)
  47. }
  48. }
  49. _, _ = domain, tld
  50. })
  51. b.Run("regexp.Split", func(b *testing.B) {
  52. b.ReportAllocs()
  53. b.ResetTimer()
  54. var domain, tld string
  55. for i := 0; i < b.N; i++ {
  56. for _, email := range emails {
  57. domain, tld = regexpSplit(email)
  58. }
  59. }
  60. _, _ = domain, tld
  61. })
  62. b.Run("strings.Cut", func(b *testing.B) {
  63. b.ReportAllocs()
  64. b.ResetTimer()
  65. var domain, tld string
  66. for i := 0; i < b.N; i++ {
  67. for _, email := range emails {
  68. domain, tld = stringsCut(email)
  69. }
  70. }
  71. _, _ = domain, tld
  72. })
  1. cpu: Intel(R) Core(TM) i7-9750H CPU @ 2.60GHz
  2. Benchmark
  3. Benchmark/strings.Split
  4. Benchmark/strings.Split-12 752 1563851 ns/op 640002 B/op 20000 allocs/op
  5. Benchmark/strings.SplitN
  6. Benchmark/strings.SplitN-12 805 1463329 ns/op 640003 B/op 20000 allocs/op
  7. Benchmark/strings.Index+strings.Split
  8. Benchmark/strings.Index+strings.Split-12 1416 858783 ns/op 320000 B/op 10000 allocs/op
  9. Benchmark/regexp.Split
  10. Benchmark/regexp.Split-12 85 14605240 ns/op 11088513 B/op 160024 allocs/op
  11. Benchmark/strings.Cut
  12. Benchmark/strings.Cut-12 6597 180579 ns/op 0 B/op 0 allocs/op
  13. PASS
英文:

Use strings.Split function

  1. email := &quot;learning@gmail.com&quot;
  2. split := strings.Split(email, &quot;@&quot;)
  3. split = strings.Split(split[1], &quot;.&quot;)
  4. fmt.Println(&quot;Domain:&quot;, split[0])
  5. fmt.Println(&quot;TLD:&quot;, split[1])

optionally you can validate an email string with mail.ParseAddress function

  1. email := &quot;learning@gmail.com&quot;
  2. addr, err := mail.ParseAddress(email)
  3. if err != nil {
  4. log.Fatal(err)
  5. }

> what if the TLD goes like this co.id, does the output still co.id ? –
@zacharyy

simply try to find the first index of . (strings.Index) and use one to separate the string

  1. email := &quot;learning@gmail.co.id&quot;
  2. split := strings.Split(email, &quot;@&quot;)
  3. index := strings.Index(split[1], &quot;.&quot;)
  4. fmt.Println(&quot;Domain:&quot;, split[1][:index])
  5. fmt.Println(&quot;TLD:&quot;, split[1][index+1:])

or use regexp.Split function

  1. email := &quot;learning@gmail.co.id&quot;
  2. split := strings.Split(email, &quot;@&quot;)
  3. split = regexp.MustCompile(&quot;[.]&quot;).
  4. Split(split[1], 2)
  5. fmt.Println(&quot;Domain:&quot;, split[0])
  6. fmt.Println(&quot;TLD:&quot;, split[1])

or strings.SplitN

  1. email := &quot;learning@gmail.co.id&quot;
  2. split := strings.Split(email, &quot;@&quot;)
  3. split = strings.SplitN(split[1], &quot;.&quot;, 2)
  4. fmt.Println(&quot;Domain:&quot;, split[0])
  5. fmt.Println(&quot;TLD:&quot;, split[1])

or strings.Cut

  1. _, host, found := strings.Cut(email, &quot;@&quot;)
  2. if !found {
  3. t.Fatal(&quot;fail cut to host (Domain + TLD)&quot;)
  4. }
  5. domain, tld, found := strings.Cut(host, &quot;.&quot;)
  6. if !found {
  7. t.Fatal(&quot;fail cut to Domain and TLD&quot;)
  8. }
  9. fmt.Println(&quot;Domain:&quot;, domain)
  10. fmt.Println(&quot;TLD:&quot;, tld)

👉🏻 <kbd>PLAYGROUND</kbd> 👈🏻

Benchmarks

  1. const (
  2. quantity = 10000
  3. userLength = 10
  4. domain = &quot;gmail.com&quot;
  5. )
  6. var (
  7. letterRunes = []rune(&quot;abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ&quot;)
  8. emails = make([]string, 0, quantity)
  9. seeded = rand.New(rand.NewSource(time.Now().UnixMilli()))
  10. )
  11. for i := 0; i &lt; quantity; i++ {
  12. user := make([]rune, userLength)
  13. for i := range user {
  14. user[i] = letterRunes[seeded.Intn(len(letterRunes))]
  15. }
  16. emails = append(emails, fmt.Sprintf(&quot;%s@%s&quot;, string(user), domain))
  17. }
  18. b.Run(&quot;strings.Split&quot;, func(b *testing.B) {
  19. b.ReportAllocs()
  20. b.ResetTimer()
  21. var domain, tld string
  22. for i := 0; i &lt; b.N; i++ {
  23. for _, email := range emails {
  24. domain, tld = stringsSplit(email)
  25. }
  26. }
  27. _, _ = domain, tld
  28. })
  29. b.Run(&quot;strings.SplitN&quot;, func(b *testing.B) {
  30. b.ReportAllocs()
  31. b.ResetTimer()
  32. var domain, tld string
  33. for i := 0; i &lt; b.N; i++ {
  34. for _, email := range emails {
  35. domain, tld = stringsSplitN(email)
  36. }
  37. }
  38. _, _ = domain, tld
  39. })
  40. b.Run(&quot;strings.Index+strings.Split&quot;, func(b *testing.B) {
  41. b.ReportAllocs()
  42. b.ResetTimer()
  43. var domain, tld string
  44. for i := 0; i &lt; b.N; i++ {
  45. for _, email := range emails {
  46. domain, tld = stringsIndexAndStringsSplit(email)
  47. }
  48. }
  49. _, _ = domain, tld
  50. })
  51. b.Run(&quot;regexp.Split&quot;, func(b *testing.B) {
  52. b.ReportAllocs()
  53. b.ResetTimer()
  54. var domain, tld string
  55. for i := 0; i &lt; b.N; i++ {
  56. for _, email := range emails {
  57. domain, tld = regexpSplit(email)
  58. }
  59. }
  60. _, _ = domain, tld
  61. })
  62. b.Run(&quot;strings.Cut&quot;, func(b *testing.B) {
  63. b.ReportAllocs()
  64. b.ResetTimer()
  65. var domain, tld string
  66. for i := 0; i &lt; b.N; i++ {
  67. for _, email := range emails {
  68. domain, tld = stringsCut(email)
  69. }
  70. }
  71. _, _ = domain, tld
  72. })
  1. cpu: Intel(R) Core(TM) i7-9750H CPU @ 2.60GHz
  2. Benchmark
  3. Benchmark/strings.Split
  4. Benchmark/strings.Split-12 752 1563851 ns/op 640002 B/op 20000 allocs/op
  5. Benchmark/strings.SplitN
  6. Benchmark/strings.SplitN-12 805 1463329 ns/op 640003 B/op 20000 allocs/op
  7. Benchmark/strings.Index+strings.Split
  8. Benchmark/strings.Index+strings.Split-12 1416 858783 ns/op 320000 B/op 10000 allocs/op
  9. Benchmark/regexp.Split
  10. Benchmark/regexp.Split-12 85 14605240 ns/op 11088513 B/op 160024 allocs/op
  11. Benchmark/strings.Cut
  12. Benchmark/strings.Cut-12 6597 180579 ns/op 0 B/op 0 allocs/op
  13. PASS

huangapple
  • 本文由 发表于 2022年11月1日 19:06:10
  • 转载请务必保留本文链接:https://go.coder-hub.com/74274942.html
匿名

发表评论

匿名网友

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

确定