Пример #1
0
func mergeChannels(in1 <-chan []complex128, in2 <-chan []complex128) chan []complex128 {
	out := make(chan []complex128)
	go func() {
		fmt.Printf("Writing...\n")
		for cIn1 := range in1 {
			cIn2 := <-in2
			if len(cIn1) != len(cIn2) {
				panic("oops, columns don't match... :(")
			}
			cOut := make([]complex128, len(cIn1), len(cIn1))
			for i := range cIn1 {
				power1, angle1 := cmplx.Polar(cIn1[i])
				power2, angle2 := cmplx.Polar(cIn2[i])
				cOut[i] = cmplx.Rect(power1, angle1)
				if i > 48 && i <= 72 {
					cOut[i] = 0
				}
				// HACK variable to stop go complaining about unused variables :(
				cIn2[i] = cmplx.Rect(power2, angle2)
			}
			out <- cOut
		}
		close(out)
	}()
	return out
}
Пример #2
0
func addPolar(a, b Polar) Polar {

	// Add polar coordinates (5,140) and (3,70)
	x := cmplx.Rect(a.radius, a.angle)
	y := cmplx.Rect(b.radius, b.angle)
	radius, angle := cmplx.Polar(x + y)
	return Polar{radius, angle}

}
Пример #3
0
func (s *Soldier) Step() {
	ref := s.refPoint()
	switch s.Current {
	case Halt:
	case ForwardMarch:
		s.Pt += complex(vel, 0)*s.Dir - ref*complex(gain, 0) +
			complex(velRand, 0)*complex(rand.Float64(), rand.Float64())
		s.P.Move(real(s.Pt), imag(s.Pt))
	case LeftWheel:
		v := velMax
		if s.Adj[0] == nil {
			_, cols := s.C.f.RowCols(len(s.C.s))
			v *= float64(cols-s.Col()+1) / float64(cols+1)
			th := velMax / (2 * math.Pi * float64(cols+1))
			s.Dir *= cmplx.Rect(1, th)
		} else {
			v = vel
		}
		s.Pt += complex(v, 0)*s.Dir - ref*complex(gain, 0) +
			complex(velRand, 0)*complex(rand.Float64(), rand.Float64())
		s.P.Move(real(s.Pt), imag(s.Pt))
	case RightWheel:
		v := velMax
		if s.Adj[0] == nil {
			_, cols := s.C.f.RowCols(len(s.C.s))
			v *= float64(s.Col()+1) / float64(cols+1)
			th := velMax / (2 * math.Pi * float64(cols+1))
			s.Dir *= cmplx.Rect(1, -th)
		} else {
			v = vel
		}
		s.Pt += complex(v, 0)*s.Dir - ref*complex(gain, 0) +
			complex(velRand, 0)*complex(rand.Float64(), rand.Float64())
		s.P.Move(real(s.Pt), imag(s.Pt))
		//	case LeftTurn, RightTurn:
		//		s.Color()
	case Reform:
		s.Pt -= ref*complex(gainRef, 0) -
			complex(velRand, 0)*complex(rand.Float64(), rand.Float64())
		s.P.Move(real(s.Pt), imag(s.Pt))
		if cmplx.Abs(s.Pt-ref) < 0.1 {
			s.Orders(Halt)
		}
	}
	if s.Adj[0] != nil {
		s.Dir = cmplx.Rect(1, cmplx.Phase(s.Adj[0].Position()-s.Position()))
	}
}
func mean_angle(deg []float64) float64 {
	sum := 0i
	for _, x := range deg {
		sum += cmplx.Rect(1, deg2rad(x))
	}
	return rad2deg(cmplx.Phase(sum))
}
Пример #5
0
func roots(n int) []complex128 {
	r := make([]complex128, n)
	for i := 0; i < n; i++ {
		r[i] = cmplx.Rect(1, 2*math.Pi*float64(i)/float64(n))
	}
	return r
}
Пример #6
0
func logInterpolate(a complex128, b complex128, proportion float64) complex128 {
	// TODO - precalc arg/norm outside the loop.
	if cmplx.Abs(a) < cmplx.Abs(b) {
		return logInterpolate(b, a, 1-proportion)
	}

	z := b / a
	zArg := cmplx.Phase(z)
	if zArg > 0 {
		// aArg -> bArg, or aArg -> bArg + 2PI, whichever is closer
		if zArg > math.Pi {
			zArg -= 2 * math.Pi
		}
	} else {
		// aArg -> bArg, or aArg -> bArg - 2PI, whichever is closer
		if zArg < -math.Pi {
			zArg += 2 * math.Pi
		}
	}

	zLogAbs := math.Log(cmplx.Abs(z))
	cArg, cLogAbs := zArg*proportion, zLogAbs*proportion
	cAbs := math.Exp(cLogAbs)
	return a * cmplx.Rect(cAbs, cArg)
}
func agm(a, g complex128) complex128 {
	for cmplx.Abs(a-g) > cmplx.Abs(a)*ε {
		a, g = (a+g)*.5, cmplx.Rect(math.Sqrt(cmplx.Abs(a)*cmplx.Abs(g)),
			(cmplx.Phase(a)+cmplx.Phase(g))*.5)
	}
	return a
}
func ditfft2(x, y []complex128, n, s int) {
	if n == 1 {
		y[0] = x[0]
		return
	}
	ditfft2(x, y, n/2, 2*s)
	ditfft2(x[s:], y[n/2:], n/2, 2*s)
	for k := 0; k < n/2; k++ {
		tf := cmplx.Rect(1, -2*math.Pi*float64(k)/float64(n)) * y[k+n/2]
		y[k], y[k+n/2] = y[k]+tf, y[k]-tf
	}
}
Пример #9
0
func TwiddleFactors(N int, ifft bool) []complex128 {
	out := make([]complex128, N)

	inv := 1
	if ifft {
		inv = -1
	}
	for i := 0; i < N/2; i++ {
		out[i] = cmplx.Rect(1, math.Pi*float64(-2*i*inv)/float64(N))
	}
	return out
}
Пример #10
0
func main() {
	i := 1

	fmt.Println("initial:", i)
	zeroval(i)

	fmt.Println("zeroval:", i)
	zeroptr(&i)

	fmt.Println("zeroptr:", i)
	fmt.Println("pointer:", &i)

	complex1 := cmplx.Rect(12, math.Pi/2)
	fmt.Println(complex1)
	add180ToComplexNumner(&complex1)
	fmt.Println(complex1)
}
Пример #11
0
// Rotate rotate the origin center
func Rotate(p complex128, rad float64) complex128 {
	return p * cmplx.Rect(1, rad)
}
Пример #12
0
// LinearMap is linear mapping
func LinearMap(u, v complex128) complex128 {
	return cmplx.Rect(cmplx.Abs(v)/cmplx.Abs(u), Angle(v, u))
}
Пример #13
0
// TODO - clean up a lot.
func NewCQKernel(params CQParams) *CQKernel {
	// Constructor
	p := Properties{}
	p.sampleRate = params.sampleRate
	p.maxFrequency = params.maxFrequency
	p.binsPerOctave = params.binsPerOctave

	// GenerateKernel
	q := params.q
	atomHopFactor := params.atomHopFactor
	thresh := params.threshold
	bpo := params.binsPerOctave

	p.minFrequency = float64(math.Pow(2, 1/float64(bpo)) * float64(params.maxFrequency) / 2.0)
	p.Q = q / (math.Pow(2, 1.0/float64(bpo)) - 1.0)

	maxNK := float64(int(math.Floor(p.Q*p.sampleRate/p.minFrequency + 0.5)))
	minNK := float64(int(math.Floor(p.Q*p.sampleRate/
		(p.minFrequency*math.Pow(2.0, (float64(bpo)-1.0)/float64(bpo))) + 0.5)))

	if minNK == 0 || maxNK == 0 {
		panic("Kernal minNK or maxNK is 0, can't make kernel")
	}

	p.atomSpacing = round(minNK*atomHopFactor + 0.5)
	p.firstCentre = p.atomSpacing * roundUp(math.Ceil(maxNK/2.0)/float64(p.atomSpacing))
	p.fftSize = nextPowerOf2(p.firstCentre + roundUp(maxNK/2.0))
	p.atomsPerFrame = roundDown(1.0 + (float64(p.fftSize)-math.Ceil(maxNK/2.0)-float64(p.firstCentre))/float64(p.atomSpacing))

	if DEBUG {
		fmt.Printf("atomsPerFrame = %v (q = %v, Q = %v, atomHopFactor = %v, atomSpacing = %v, fftSize = %v, maxNK = %v, firstCentre = %v)\n",
			p.atomsPerFrame, q, p.Q, atomHopFactor, p.atomSpacing, p.fftSize, maxNK, p.firstCentre)
	}

	p.lastCentre = p.firstCentre + (p.atomsPerFrame-1)*p.atomSpacing
	p.fftHop = (p.lastCentre + p.atomSpacing) - p.firstCentre

	if DEBUG {
		fmt.Printf("fftHop = %v\n", p.fftHop)
	}

	dataSize := p.binsPerOctave * p.atomsPerFrame

	kernel := Kernel{
		make([]int, 0, dataSize),
		make([][]complex128, 0, dataSize),
	}

	for k := 1; k <= p.binsPerOctave; k++ {
		nk := int(p.Q*p.sampleRate/(p.minFrequency*math.Pow(2, ((float64(k)-1.0)/float64(bpo)))) + 0.5)

		win := makeWindow(params.window, nk)

		fk := float64(p.minFrequency * math.Pow(2, ((float64(k)-1.0)/float64(bpo))))

		cmplxs := make([]complex128, nk, nk)
		for i := 0; i < nk; i++ {
			arg := (2.0 * math.Pi * fk * float64(i)) / p.sampleRate
			cmplxs[i] = cmplx.Rect(win[i], arg)
		}

		atomOffset := p.firstCentre - roundUp(float64(nk)/2.0)

		for i := 0; i < p.atomsPerFrame; i++ {
			shift := atomOffset + (i * p.atomSpacing)
			cin := make([]complex128, p.fftSize, p.fftSize)
			for j := 0; j < nk; j++ {
				cin[j+shift] = cmplxs[j]
			}

			cout := fft.FFT(cin)

			// Keep this dense for the moment (until after normalisation calculations)
			for j := 0; j < p.fftSize; j++ {
				if cmplx.Abs(cout[j]) < thresh {
					cout[j] = complex(0, 0)
				} else {
					cout[j] = complexTimes(cout[j], 1.0/float64(p.fftSize))
				}
			}

			kernel.origin = append(kernel.origin, 0)
			kernel.data = append(kernel.data, cout)
		}
	}

	if DEBUG {
		fmt.Printf("size = %v * %v (fft size = %v)\n", len(kernel.data), len(kernel.data[0]), p.fftSize)
	}

	// finalizeKernel

	// calculate weight for normalisation
	wx1 := maxidx(kernel.data[0])
	wx2 := maxidx(kernel.data[len(kernel.data)-1])

	subset := make([][]complex128, len(kernel.data), len(kernel.data))
	for i := 0; i < len(kernel.data); i++ {
		subset[i] = make([]complex128, 0, wx2-wx1+1)
	}
	for j := wx1; j <= wx2; j++ {
		for i := 0; i < len(kernel.data); i++ {
			subset[i] = append(subset[i], kernel.data[i][j])
		}
	}

	// Massive hack - precalculate above instead :(
	nrows, ncols := len(subset), len(subset[0])

	square := make([][]complex128, ncols, ncols) // conjugate transpose of subset * subset
	for i := 0; i < ncols; i++ {
		square[i] = make([]complex128, ncols, ncols)
	}

	for j := 0; j < ncols; j++ {
		for i := 0; i < ncols; i++ {
			v := complex(0, 0)
			for k := 0; k < nrows; k++ {
				v += subset[k][i] * cmplx.Conj(subset[k][j])
			}
			square[i][j] = v
		}
	}

	wK := []float64{}
	for i := int(1.0/q + 0.5); i < ncols-int(1.0/q+0.5)-2; i++ {
		wK = append(wK, cmplx.Abs(square[i][i]))
	}

	weight := float64(p.fftHop) / float64(p.fftSize)
	if len(wK) > 0 {
		weight /= mean(wK)
	}
	weight = math.Sqrt(weight)

	if DEBUG {
		fmt.Printf("weight = %v (from %v elements in wK, ncols = %v, q = %v)\n",
			weight, len(wK), ncols, q)
	}

	// apply normalisation weight, make sparse, and store conjugate
	// (we use the adjoint or conjugate transpose of the kernel matrix
	// for the forward transform, the plain kernel for the inverse
	// which we expect to be less common)

	sk := Kernel{
		make([]int, len(kernel.data), len(kernel.data)),
		make([][]complex128, len(kernel.data), len(kernel.data)),
	}
	for i := 0; i < len(kernel.data); i++ {
		sk.origin[i] = 0
		sk.data[i] = []complex128{}

		lastNZ := 0
		for j := len(kernel.data[i]) - 1; j >= 0; j-- {
			if cmplx.Abs(kernel.data[i][j]) != 0 {
				lastNZ = j
				break
			}
		}

		haveNZ := false
		for j := 0; j <= lastNZ; j++ {
			if haveNZ || cmplx.Abs(kernel.data[i][j]) != 0 {
				if !haveNZ {
					sk.origin[i] = j
				}
				haveNZ = true
				sk.data[i] = append(sk.data[i],
					complexTimes(cmplx.Conj(kernel.data[i][j]), weight))
			}
		}
	}

	return &CQKernel{p, &sk}
}
Пример #14
0
func (Polar) CognizePolar(eye *be.Eye, v interface{}) {
	x := v.(Circuit)
	eye.Show("Complex", cmplx.Rect(x.FloatAt("R"), x.FloatAt("Theta")))
}
Пример #15
0
// randomComplex returns a random complex128
func randomComplex() complex128 {
	return cmplx.Rect(randomFloat(), randomFloat())
}
Пример #16
0
func add180ToComplexNumner(complexNumber *complex128) {
	r, θ := cmplx.Polar(*complexNumber)
	*complexNumber = cmplx.Rect(r, θ+math.Pi/2)
}
Пример #17
0
func (s *Soldier) Row() int {
	if s.Adj[0] == nil {
		return 0
	}
	return s.Adj[0].Row() + 1
}
*/
func (s *Soldier) Col() int {
	if s.Adj[1] == nil {
		return 1
	}
	return s.Adj[1].Col() + 1
}

var (
	left  complex128 = cmplx.Rect(1, 0.5*math.Pi)
	right complex128 = cmplx.Rect(1, -0.5*math.Pi)
)

func (s *Soldier) refPoint() complex128 {
	var pt, tmp, dir complex128
	if s.Adj[0] != nil {
		dir = s.Dir * left * left
		tmp = s.Adj[0].Position()
		pt += s.Pt - tmp - complex(spacing, 0)*dir
	}
	if s.Adj[3] != nil && s.ByLeft {
		dir = s.Dir * right
		tmp = s.Adj[3].Position()
		pt += s.Pt - tmp - complex(spacing, 0)*dir
	}