diff options
Diffstat (limited to 'forces/forces.go')
-rw-r--r-- | forces/forces.go | 62 |
1 files changed, 28 insertions, 34 deletions
diff --git a/forces/forces.go b/forces/forces.go index e3f822d..7763f87 100644 --- a/forces/forces.go +++ b/forces/forces.go @@ -10,15 +10,15 @@ import ( // forces_acting calculates the force inbetween the two given stars s1 and s2 // The function return the force -func forceActing(s1 structs.Star, s2 structs.Star) structs.Force { +func forceActing(s1 structs.Star2D, s2 structs.Star2D) structs.Force { // Gravitational constant var G float64 = 6.674e-11 // Distance between the stars - var r21 = math.Sqrt(math.Pow(s2.C.X-s1.C.X, 2) + math.Pow(s2.C.Y-s1.C.Y, 2) + math.Pow(s2.C.Z-s1.C.Z, 2)) + var r21 = math.Sqrt(math.Pow(s2.C.X-s1.C.X, 2) + math.Pow(s2.C.Y-s1.C.Y, 2)) // Unit vector pointing from s1 to s2 - rhat := structs.Force{s2.C.X - s1.C.X, s2.C.Y - s1.C.Y, s2.C.Z - s1.C.Z} + rhat := structs.Force{s2.C.X - s1.C.X, s2.C.Y - s1.C.Y} // Calculate how strong the star is affected var FScalar = G * (s1.Mass * s2.Mass) / math.Pow(math.Abs(r21), 2) @@ -26,16 +26,15 @@ func forceActing(s1 structs.Star, s2 structs.Star) structs.Force { // Calculate the overall force by combining the scalar and the vector var Fx = FScalar * rhat.X var Fy = FScalar * rhat.Y - var Fz = FScalar * rhat.Z // Pack the forces in a force structur - F := structs.Force{Fx, Fy, Fz} + F := structs.Force{Fx, Fy} return F } // forces calculates the forces acting in between a given star and all the other stars in a given array. -func forces(stars_arr []structs.Star, nr int) structs.Force { +func forces(stars_arr []structs.Star2D, nr int) structs.Force { var force structs.Force // Iterate over all the stars in the stars_arr @@ -48,11 +47,9 @@ func forces(stars_arr []structs.Star, nr int) structs.Force { fa := forceActing(stars_arr[nr], stars_arr[index]) stars_arr[nr].F.X += fa.X stars_arr[nr].F.Y += fa.Y - stars_arr[nr].F.Z += fa.Z force.X += fa.X force.Y += fa.Y - force.Z += fa.Z } } @@ -61,31 +58,31 @@ func forces(stars_arr []structs.Star, nr int) structs.Force { // forcesThread calculates the forces acting on a given amount of stars in a given range for a given slice of stars // as a go-routine -func forcesThread(starSlice []structs.Star, localRangeStart int, localRangeEnd int, channel chan structs.Star) { +func forcesThread(starSlice []structs.Star2D, localRangeStar2Dt int, localRangeEnd int, channel chan structs.Star2D) { // iterate over the given range - for index := localRangeStart; index < localRangeEnd; index++ { + for index := localRangeStar2Dt; index < localRangeEnd; index++ { // Calculate the force acting inbetween the given star and all other stars var force = forces(starSlice, index) // create a new star - newStar := structs.Star{ - structs.Coord{starSlice[index].C.X, starSlice[index].C.Y, starSlice[index].C.Z}, - structs.Force{force.X, force.Y, force.Z}, + newStar2D := structs.Star2D{ + structs.Coord{starSlice[index].C.X, starSlice[index].C.Y}, + structs.Force{force.X, force.Y}, starSlice[index].Mass, } - // push the new Star into the channel - channel <- newStar + // push the new Star2D into the channel + channel <- newStar2D } } // CalcAllForces calculates all the forces acting inbetween all the stars in the given starSlice slice and // returns a "new" slice contaning the forces -func CalcAllForces(starSlice []structs.Star, threads int) []structs.Star { +func CalcAllForces(starSlice []structs.Star2D, threads int) []structs.Star2D { // create a channel for bundling the stars generaten in the go-routines - channel := make(chan structs.Star, 1000) + channel := make(chan structs.Star2D, 1000) sliceLength := len(starSlice) @@ -94,7 +91,7 @@ func CalcAllForces(starSlice []structs.Star, threads int) []structs.Star { localRangeLen := sliceLength / threads // generate a new slice for storing the stars - var newSlice []structs.Star + var newSlice []structs.Star2D llog.Good(fmt.Sprintf("Starting %d workers, each processing %d stars", threads, localRangeLen)) @@ -102,39 +99,37 @@ func CalcAllForces(starSlice []structs.Star, threads int) []structs.Star { for i := 0; i < threads; i++ { // define the local range - localRangeStart := i * localRangeLen + localRangeStar2Dt := i * localRangeLen localRangeEnd := (i * localRangeLen) + localRangeLen // calculate the forces for all the stars in the given slice in the given range and return them using the // given channel - go forcesThread(starSlice, localRangeStart, localRangeEnd, channel) + go forcesThread(starSlice, localRangeStar2Dt, localRangeEnd, channel) } // Handle errors (10004 stars, but 1250 stars per thread, so 4 stars are not calculate and block the queue) if sliceLength > localRangeLen { // Calculate the amount of stars and their range - remainingStars := sliceLength - (localRangeLen * threads) + remainingStar2Ds := sliceLength - (localRangeLen * threads) localRangeEnd := ((threads - 1) * localRangeLen) + localRangeLen // Run the Thread - // go forcesThread(starSlice, localRangeEnd, localRangeEnd+remainingStars, channel) - forcesThread(starSlice, localRangeEnd, localRangeEnd+remainingStars, channel) + // go forcesThread(starSlice, localRangeEnd, localRangeEnd+remainingStar2Ds, channel) + forcesThread(starSlice, localRangeEnd, localRangeEnd+remainingStar2Ds, channel) } // Initialize a new progress bar - bar := pb.New(len(starSlice)).Prefix("Stars: ") - - bar.Start() + bar := pb.New(len(starSlice)).Prefix("Star2Ds: ") // iterate over the amount of stars for i := 0; i < sliceLength; i++ { // block until a star is finisehd - var newStar structs.Star = <-channel + var newStar2D structs.Star2D = <-channel // append the star from the channel to the newSlice for returning in the end - newSlice = append(newSlice, newStar) + newSlice = append(newSlice, newStar2D) // increment the progress bar and the counter bar.Increment() @@ -146,9 +141,9 @@ func CalcAllForces(starSlice []structs.Star, threads int) []structs.Star { } // Calculate the new positions of the stars using the -func NextTimestep(starSlice []structs.Star, deltat int) []structs.Star { +func NextTimestep(starSlice []structs.Star2D, deltat int) []structs.Star2D { // create a new slice for storing the "new" stars - var newSlice []structs.Star + var newSlice []structs.Star2D // iterate over all the stars in the old slice for index := range starSlice { @@ -156,17 +151,16 @@ func NextTimestep(starSlice []structs.Star, deltat int) []structs.Star { // calculate the new position newX := starSlice[index].C.X + starSlice[index].F.X*float64(deltat) newY := starSlice[index].C.Y + starSlice[index].F.Y*float64(deltat) - newZ := starSlice[index].C.Z + starSlice[index].F.Z*float64(deltat) // assemble the new star - newStar := structs.Star{ - C: structs.Coord{X: newX, Y: newY, Z: newZ}, + newStar2D := structs.Star2D{ + C: structs.Coord{X: newX, Y: newY}, F: structs.Force{}, Mass: starSlice[index].Mass, } // append the new star to the newSlice - newSlice = append(newSlice, newStar) + newSlice = append(newSlice, newStar2D) } return newSlice |