将Project Euler #8移植到Go语言

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

Porting Project Euler #8 to Go

问题

我正在尝试学习Go语言,并决定使用Project Euler来帮助我。我之前已经用JavaScript解决了一些问题。我现在正试图将第8题转换成Go语言。

以下是JavaScript版本的代码:

var n = "7316717653133062491922511967442657474235534919493496983520312774506326239578318016984801869478851843858615607891129494954595017379583319528532088055111254069874715852386305071569329096329522744304355766896648950445244523161731856403098711121722383113622298934233803081353362766142828064444866452387493035890729629049156044077239071381051585930796086670172427121883998797908792274921901699720888093776657273330010533678812202354218097512545405947522435258490771167055601360483958644670632441572215539753697817977846174064955149290862569321978468622482839722413756570560574902614079729686524145351004748216637048440319989000889524345065854122758866688116427171479924442928230863465674813919123162824586178664583591245665294765456828489128831426076900422421902267105562632111110937054421750694165896040807198403850962455444362981230987879927244284909188845801561660979191338754992005240636899125607176060588611646710940507754100225698315520005593572972571636269561882670428252483600823257530420752963450";

// 将输入字符串转换为数组
n = n.split("");

// 遍历每个长度为13的子数组,并计算乘积,同时记录最大值
var largest = 0;
for (var i = 0; i < (n.length - 12); i++) {
    var b = n.slice(i, i + 13);
    var product = b.reduce(function(prev, current) {
        return prev * Number(current);
    }, 1);
    if (product > largest) {
        largest = product;
    }
}
console.log(largest);

以下是我用Go语言转换的代码:

import (
	"fmt"
	"strconv"
	"strings"
)

var data string = "7316717653133062491922511967442657474235534919493496983520312774506326239578318016984801869478851843858615607891129494954595017379583319528532088055111254069874715852386305071569329096329522744304355766896648950445244523161731856403098711121722383113622298934233803081353362766142828064444866452387493035890729629049156044077239071381051585930796086670172427121883998797908792274921901699720888093776657273330010533678812202354218097512545405947522435258490771167055601360483958644670632441572215539753697817977846174064955149290862569321978468622482839722413756570560574902614079729686524145351004748216637048440319989000889524345065854122758866688116427171479924442928230863465674813919123162824586178664583591245665294765456828489128831426076900422421902267105562632111110937054421750694165896040807198403850962455444362981230987879927244284909188845801561660979191338754992005240636899125607176060588611646710940507754100225698315520005593572972571636269561882670428252483600823257530420752963450"

func main() {
	// 将字符串转换为整数数组
	var grid []int
	var stringGrid []string = strings.Split(data, "")
	for i := 0; i < 1000; i++ {
		cell, _ := strconv.Atoi(stringGrid[i])
		grid = append(grid, cell)
	}

	// 找到最大值
	largest := 0
	for i := 0; i < len(grid)-12; i++ {
		a := grid[i : i+13]
		total := 1
		for b := 0; b < len(a); b++ {
			total *= a[b]
		}
		if total > largest {
			largest = total
		}
	}
	fmt.Println(largest)
}

我无法找出问题所在,如果我在两个版本中添加了一些打印语句,它们会输出相同的数字序列,但是Go版本似乎没有正确进行乘法运算?我已经仔细检查过了。肯定有一些小细节我忽略了吗?

英文:

I am trying to learn Go, and I decided to use Project Euler to help me. I have previously solved some of the problems in Javascript. I am trying to port #8 to Go.

Here it is in Javascript

var n = &quot;7316717653133062491922511967442657474235534919493496983520312774506326239578318016984801869478851843858615607891129494954595017379583319528532088055111254069874715852386305071569329096329522744304355766896648950445244523161731856403098711121722383113622298934233803081353362766142828064444866452387493035890729629049156044077239071381051585930796086670172427121883998797908792274921901699720888093776657273330010533678812202354218097512545405947522435258490771167055601360483958644670632441572215539753697817977846174064955149290862569321978468622482839722413756570560574902614079729686524145351004748216637048440319989000889524345065854122758866688116427171479924442928230863465674813919123162824586178664583591245665294765456828489128831426076900422421902267105562632111110937054421750694165896040807198403850962455444362981230987879927244284909188845801561660979191338754992005240636899125607176060588611646710940507754100225698315520005593572972571636269561882670428252483600823257530420752963450&quot;;

// Split our input into an array
n = n.split(&quot;&quot;);

// Loop through every 13 length chuck multiplying them. Keep track of the largest
var largest = 0;
for (var i = 0; i &lt; (n.length - 12); i++) {
    var b = n.slice(i, i + 13);
    var product = b.reduce(function(prev, current) {
        return prev * Number(current);
    }, 1);
    if (product &gt; largest) {
        largest = product;
    }
}
console.log(largest);

And here is my port in Go

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

var data string = &quot;7316717653133062491922511967442657474235534919493496983520312774506326239578318016984801869478851843858615607891129494954595017379583319528532088055111254069874715852386305071569329096329522744304355766896648950445244523161731856403098711121722383113622298934233803081353362766142828064444866452387493035890729629049156044077239071381051585930796086670172427121883998797908792274921901699720888093776657273330010533678812202354218097512545405947522435258490771167055601360483958644670632441572215539753697817977846174064955149290862569321978468622482839722413756570560574902614079729686524145351004748216637048440319989000889524345065854122758866688116427171479924442928230863465674813919123162824586178664583591245665294765456828489128831426076900422421902267105562632111110937054421750694165896040807198403850962455444362981230987879927244284909188845801561660979191338754992005240636899125607176060588611646710940507754100225698315520005593572972571636269561882670428252483600823257530420752963450&quot;

func main() {
	// Get an array of ints
	var grid []int
	var stringGrid []string = strings.Split(data, &quot;&quot;)
	for i := 0; i &lt; 1000; i++ {
		cell, _ := strconv.Atoi(stringGrid[i])
		grid = append(grid, cell)
	}

	// Find the largest one
	largest := 0
	for i := 0; i &lt; len(grid)-12; i++ {
		a := grid[i : i+13]
		total := 1
		for b := 0; b &lt; len(a); b++ {
			total *= a[b]
		}
		if total &gt; largest {
			largest = total
		}
	}
	fmt.Println(largest)
}

I can't find out what is wrong, if I add a bunch of prints to both of them, the spit out the same sequences of numbers, but the Go one doesn't seem to be doing the multiplication right?!? I double checked by hand. There must be some small thing I am missing?

答案1

得分: 4

你遇到了整数溢出问题。所有的 JavaScript 数字都是 64 位双精度浮点数,因此具有 53 位整数精度。在 Go 中,int 类型根据处理器的不同可以是 32 位或 64 位。对于你来说,int 是 32 位,所以无法存储像解决方案那么大的数字。你可以通过使用 int32int64 类型来指定要使用的整数大小。下面是修正后的程序。有关整数溢出的更多信息,请参见这里。有关 Go 规范中相关部分,请参见这里

package main

import (
	"fmt"
	"strconv"
	"strings"
)

var data string = "7316717653133062491922511967442657474235534919493496983520312774506326239578318016984801869478851843858615607891129494954595017379583319528532088055111254069874715852386305071569329096329522744304355766896648950445244523161731856403098711121722383113622298934233803081353362766142828064444866452387493035890729629049156044077239071381051585930796086670172427121883998797908792274921901699720888093776657273330010533678812202354218097512545405947522435258490771167055601360483958644670632441572215539753697817977846174064955149290862569321978468622482839722413756570560574902614079729686524145351004748216637048440319989000889524345065854122758866688116427171479924442928230863465674813919123162824586178664583591245665294765456828489128831426076900422421902267105562632111110937054421750694165896040807198403850962455444362981230987879927244284909188845801561660979191338754992005240636899125607176060588611646710940507754100225698315520005593572972571636269561882670428252483600823257530420752963450"

func main() {
	// 获取一个整数数组
	var grid []int64
	var stringGrid = strings.Split(data, "")
	for i := 0; i < 1000; i++ {
		cell, _ := strconv.Atoi(stringGrid[i])
		grid = append(grid, int64(cell))
	}

	// 找到最大的数
	var largest int64
	for i := 0; i < len(grid)-12; i++ {
		a := grid[i : i+13]
		var total int64 = 1
		for b := 0; b < len(a); b++ {
			total *= a[b]
		}
		if total > largest {
			largest = total
		}
	}
	fmt.Println(largest)
}
英文:

You're running into integer overflow. All javascript numbers are 64-bit doubles, and therefore have 53 bits of integer precision. In Go, the int type is either 32-bit or 64-bit depending on your processor. For you, int is 32 bit, so it cannot store a number as large as the solution. You can specify what size integers to use by using the int32 and int64 types. Below is the corrected program. See here for more info on integer overflow. here for the relevant section in the Go specification.

package main

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

var data string = &quot;7316717653133062491922511967442657474235534919493496983520312774506326239578318016984801869478851843858615607891129494954595017379583319528532088055111254069874715852386305071569329096329522744304355766896648950445244523161731856403098711121722383113622298934233803081353362766142828064444866452387493035890729629049156044077239071381051585930796086670172427121883998797908792274921901699720888093776657273330010533678812202354218097512545405947522435258490771167055601360483958644670632441572215539753697817977846174064955149290862569321978468622482839722413756570560574902614079729686524145351004748216637048440319989000889524345065854122758866688116427171479924442928230863465674813919123162824586178664583591245665294765456828489128831426076900422421902267105562632111110937054421750694165896040807198403850962455444362981230987879927244284909188845801561660979191338754992005240636899125607176060588611646710940507754100225698315520005593572972571636269561882670428252483600823257530420752963450&quot;

func main() {
	// Get an array of ints
	var grid []int64
	var stringGrid = strings.Split(data, &quot;&quot;)
	for i := 0; i &lt; 1000; i++ {
		cell, _ := strconv.Atoi(stringGrid[i])
		grid = append(grid, int64(cell))
	}

	// Find the largest one
	var largest int64
	for i := 0; i &lt; len(grid)-12; i++ {
		a := grid[i : i+13]
		var total int64 = 1
		for b := 0; b &lt; len(a); b++ {
			total *= a[b]
		}
		if total &gt; largest {
			largest = total
		}
	}
	fmt.Println(largest)
}

huangapple
  • 本文由 发表于 2014年11月13日 01:54:48
  • 转载请务必保留本文链接:https://go.coder-hub.com/26893381.html
匿名

发表评论

匿名网友

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

确定