Go语言:从一组数字中搜索x位数,为什么执行时间非常长?

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

Go lang : search x digits from sets of numbers, why takes very long time to execute?

问题

我尝试编写了一些小程序,用于从一组数字中找到 x 位数,例如:我想要从 1 到 1000000000 中找到第 89 位的数字。

以下是我的代码:

package main

import (
    "fmt"
    "strconv"
)

var bucket string

func main() {
    findDigits(89, 1000000000)
}

func findDigits(digits int, length int) {
    for i := 1; i <= length; i++ {
        bucket += strconv.Itoa(i)
    }
    fmt.Println("The", digits, "th digit from 1 -", length, "is:", string([]rune(bucket)[digits-1]))
}

有人知道我犯了什么错误吗?我需要一些建议来改进这段代码。

谢谢 Go语言:从一组数字中搜索x位数,为什么执行时间非常长?

英文:

I tried to make small programs that find x digits from sets of numbers, for example : i want to find 89th digits from 1 - 1000000000.

Here is my code : https://play.golang.org/p/93yh_urX16

package main

import (

    &quot;fmt&quot;
    &quot;strconv&quot;

)

var bucket string

func main() {

    findDigits( 89, 1000000000 )

}

func findDigits( digits int, length int) {

    for i := 1; i &lt;= length; i++ {
    
        bucket += strconv.Itoa(i)
    
    }

    fmt.Println( &quot;The&quot;, digits, &quot;th digit from 1&quot;, &quot;-&quot;, length, &quot;is :&quot;, string ( [] rune ( bucket )[digits - 1] ) )

}

Does anyone knows, what mistakes i've made ? i need some advice to me for improving this code.

Thanks Go语言:从一组数字中搜索x位数,为什么执行时间非常长?

答案1

得分: 1

你的程序非常非常低效。user1431317的程序也非常低效。

只需简单计算数值即可。即使对于像9,223,372,036,854,775,807这样的数字索引(在我的计算机上只需95.6纳秒和2次内存分配),它只需要几纳秒的CPU时间和几次内存分配。例如,

package main

import (
	"fmt"
	"math"
	"strconv"
)

// digit返回从连接的非负整数序列中的第i个数字。
// 数字序列是01234567891011121314151617181920...
func digit(i int64) string {
	// 有9个一位数的正整数,90个两位数,
	// 900个三位数,依此类推。
	if i <= 0 {
		return "0"
	}
	j := int64(1)
	w := 1
	for {
		t := j + 9*int64(math.Pow10(w-1))*int64(w)
		if t < 0 || t > i {
			break
		}
		j = t
	}
	k := i - j
	n := k / int64(w)
	m := k % int64(w)
	d := strconv.FormatInt(int64(math.Pow10(w-1))+n, 10)[m]
	return string(d)
}

func main() {
	tests := []int64{
		0, 1, 2, 3, 4, 5, 6, 7, 8, 9,
		10, 11, 12, 13,
		88, 89,
		188, 189, 190, 191, 192,
		math.MaxInt32, math.MaxInt64,
	}
	for _, n := range tests {
		fmt.Println(n, digit(n))
	}
}

输出:

0 0
1 1
2 2
3 3
4 4
5 5
6 6
7 7
8 8
9 9
10 1
11 0
12 1
13 1
88 4
89 9
188 9
189 9
190 1
191 0
192 0
2147483647 2
9223372036854775807 9
英文:

Your program is very, very inefficient. user1431317's program is very inefficient.

Simply calculate the value. It will only take nanoseconds of CPU time and a few memory allocations, even for a digit index as large as 9,223,372,036,854,775,807 (95.6 nanoseconds and 2 allocations on my computer). For example,

package main

import (
	&quot;fmt&quot;
	&quot;math&quot;
	&quot;strconv&quot;
)

// digit returns the ith digit from the sequence of
// concatenated non-negative integers.
// The sequence of digits is 01234567891011121314151617181920...
func digit(i int64) string {
	// There are 9 one digit positive integers, 90 two digit,
	// 900 three digit, and so on.
	if i &lt;= 0 {
		return &quot;0&quot;
	}
	j := int64(1)
	w := 1
	for ; ; w++ {
		t := j + 9*int64(math.Pow10(w-1))*int64(w)
		if 0 &gt; t || t &gt; i {
			break
		}
		j = t
	}
	k := i - j
	n := k / int64(w)
	m := k % int64(w)
	d := strconv.FormatInt(int64(math.Pow10(w-1))+n, 10)[m]
	return string(d)
}

func main() {
	tests := []int64{
		0, 1, 2, 3, 4, 5, 6, 7, 8, 9,
		10, 11, 12, 13,
		88, 89,
		188, 189, 190, 191, 192,
		math.MaxInt32, math.MaxInt64,
	}
	for _, n := range tests {
		fmt.Println(n, digit(n))
	}
}

Output:

0 0
1 1
2 2
3 3
4 4
5 5
6 6
7 7
8 8
9 9
10 1
11 0
12 1
13 1
88 4
89 9
188 9
189 9
190 1
191 0
192 0
2147483647 2
9223372036854775807 9

huangapple
  • 本文由 发表于 2016年3月24日 19:08:14
  • 转载请务必保留本文链接:https://go.coder-hub.com/36198738.html
匿名

发表评论

匿名网友

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

确定