如何在Go语言中求立方根?

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

How to take a cube root in Go?

问题

我正在使用牛顿法在Google Go中编写一个立方根函数。我想使用math/cmplx.Pow()来检查结果,但是我无论如何都搞不明白怎么做。我该怎么做?

英文:

I'm writing a cube root function in Google Go using Newton's method. I want to check the results using math/cmplx.Pow(), but for the life of me, I can't figure out how. How do I do this?

答案1

得分: 16

你尝试过 myCubicRootOfx = Pow(x, 1.0/3) 吗?

编辑:感谢 Jason McCreary 的评论:
我们不能使用 1/3 作为 Pow 的第二个参数,因为这是一个整数除法,所以不能得到期望的 1/3 值。通过使用 1.0/31/3.0 等,我们可以有效地得到一个带有 0.333333... 值的浮点数。

英文:

Have you tried myCubicRootOfx = Pow(x, 1.0/3) ?

edited: thanks to Jason McCreary comment:<br>
We cannot use 1/3 as the 2nd parameter to Pow as this is a integer division and hence doesn't produce the expected 1/3 value. By using 1.0/3 or 1/3.0 etc. we effectively produce a float with the 0.333333... value.

答案2

得分: 9

我使用牛顿法编写了立方根函数,作为Go Tour Exercise 47的一部分。也许下面的两个函数(Cbrt1Cbrt)会有所帮助。

package main

import (
    "fmt"
    "math/cmplx"
)

// 使用牛顿法的立方根函数,希望在20次迭代内收敛
func Cbrt1(x complex128) complex128 {
    var z complex128 = x
    for i:= 0; i < 20; i++ {
    	z = z - ((z*z*z - x) / (3.0*z*z))
    }
    return z
}

// 使用牛顿法的立方根函数,直到稳定为止
func Cbrt(x complex128) complex128 {
    var z, z0 complex128 = x, x
    for {
	    z = z - ((z*z*z - x) / (3.0*z*z))
        if cmplx.Abs(z - z0) < 1e-10 {
            break
        }
        z0 = z
    }
    return z
}

func main() {
    fmt.Println(Cbrt(2.0) , "should match" , cmplx.Pow(2, 1.0/3.0))
}
英文:

I wrote the cube root function using Newton's method as part of the Go Tour Exercise 47. Perhaps the two functions below (Cbrt1 and Cbrt) are helpful.

package main

import (
    &quot;fmt&quot;
    &quot;math/cmplx&quot;
)

// Newton&#39;s method cube root function that hopes for
//   convergence within 20 iterations
func Cbrt1(x complex128) complex128 {
    var z complex128 = x
    for i:= 0; i &lt; 20; i++ {
    	z = z - ((z*z*z - x) / (3.0*z*z))
    }
    return z
}

// Newton&#39;s method cube root function that runs until stable
func Cbrt(x complex128) complex128 {
    var z, z0 complex128 = x, x
    for {
	    z = z - ((z*z*z - x) / (3.0*z*z))
        if cmplx.Abs(z - z0) &lt; 1e-10 {
            break
        }
        z0 = z
    }
    return z
}

func main() {
    fmt.Println(Cbrt(2.0) , &quot;should match&quot; , cmplx.Pow(2, 1.0/3.0))
}

答案3

得分: 2

由于您正在使用牛顿法,我假设您从一个正实数开始。

所以您不需要复数。

您可以简单地执行以下操作:

package main

import (
    "fmt"
    "math"
)

func main() {
    x := 100.0
    root := math.Pow(x, 1.0/3.0)
    fmt.Println(root)
}
英文:

As you're using Newton's method, I suppose you're starting with a positive real number.

So you don't need complex numbers.

You may simply do

package main

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

func main() {
    x := 100.0
    root := math.Pow(x, 1.0/3.0)
    fmt.Println(root)
}

答案4

得分: 2

看起来Go语言最近的变化比其他答案要多,所以我想更新一下 - 他们将立方根内置到math包中,命名为Cbrt。它接受一个float64类型的参数,并返回一个float64类型的结果。可以在godoc math | grep Cbrt中快速查找参考(如果你已经安装了godoc,我强烈推荐这样做)

import "math"

func main() {
    var x float64 = math.Cbrt(8)
    fmt.Println(x) // 输出2
}
英文:

Looks like go has changed more recently than some of the other answers, so I figured I would update - they built cuberoot right into math as Cbrt. It takes, and returns, a float64. A quick reference is at godoc math | grep Cbrt (if you've got godoc installed, which I highly recommend)

import &quot;math&quot;

func main() {
    var x float64 = math.Cbrt(8)
    fmt.Println(x) // prints 2
}

答案5

得分: 1

例如,

package main

import (
	"fmt"
	"math/cmplx"
)

func main() {
	var x complex128
	x = -8
	y := cmplx.Pow(x, 1.0/3.0)
	fmt.Println(y)
	x = -27i
	y = cmplx.Pow(x, 1.0/3.0)
	fmt.Println(y)
	x = -8 - 27i
	y = cmplx.Pow(x, 1.0/3.0)
	fmt.Println(y)
	x = complex(-8, -27)
	y = cmplx.Pow(x, 1.0/3.0)
	fmt.Println(y)
}

输出:

(1+1.732050807568877i)
(2.5980762113533156-1.4999999999999996i)
(2.4767967587776756-1.7667767800295509i)
(2.4767967587776756-1.7667767800295509i)

Go编程语言规范

cmplx包

英文:

For example,

package main

import (
	&quot;fmt&quot;
	&quot;math/cmplx&quot;
)

func main() {
	var x complex128
	x = -8
	y := cmplx.Pow(x, 1.0/3.0)
	fmt.Println(y)
	x = -27i
	y = cmplx.Pow(x, 1.0/3.0)
	fmt.Println(y)
	x = -8 - 27i
	y = cmplx.Pow(x, 1.0/3.0)
	fmt.Println(y)
	x = complex(-8, -27)
	y = cmplx.Pow(x, 1.0/3.0)
	fmt.Println(y)
}

Output:

(1+1.732050807568877i)
(2.5980762113533156-1.4999999999999996i)
(2.4767967587776756-1.7667767800295509i)
(2.4767967587776756-1.7667767800295509i)

The Go Programming Language Specification

Package cmplx

答案6

得分: 0

尝试类似这样的代码:

package main

import(
    "fmt"
    "math/cmplx"
)


func Cbrt(x complex128) complex128 {
    z := complex128(1)
 
   
    for i:=0;i<100;i++ {  // 或者只写 for{,因为在最坏情况下你会超过 complex128
        last_z := z
        
        z = z - ((z*z*z - x)/(3 *z*z))    
        if last_z == z{
            return z
        }
    }
    return z
}

func main() {
    fmt.Println("good enough", Cbrt(9))
    fmt.Println("builtin", cmplx.Pow(9, 1.0/3.0))
}
英文:

try something like this

package main

import(
    	&quot;fmt&quot;
        &quot;math/cmplx&quot;
    )


func Cbrt(x complex128) complex128 {
    z := complex128(1)
 
   
    for i:=0;i&lt;100;i++ {  // OR JUST for{ since you will outrun complex128 in worth case
      last_z := z
        
      z = z - ((z*z*z - x)/(3 *z*z))    
      if last_z == z{
        return z
      }
    }
    return z
}

func main() {
    fmt.Println(&quot;good enough&quot;, Cbrt(9))
    fmt.Println(&quot;builtin&quot;, cmplx.Pow(9, 1.0/3.0))
}

huangapple
  • 本文由 发表于 2012年11月7日 13:15:37
  • 转载请务必保留本文链接:https://go.coder-hub.com/13263477.html
匿名

发表评论

匿名网友

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

确定