Skip to content

Instantly share code, notes, and snippets.

@timsneath
Created November 17, 2020 02:05
Show Gist options
  • Save timsneath/b2e3a914bd39d0408d0580c42ef2e58b to your computer and use it in GitHub Desktop.
Save timsneath/b2e3a914bd39d0408d0580c42ef2e58b to your computer and use it in GitHub Desktop.
import 'dart:async';
import 'dart:math' show Random;
main() async {
print('Compute π using the Monte Carlo method.');
await for (final estimate in computePi().take(100)) {
print('π ≅ $estimate');
}
}
/// Generates a stream of increasingly accurate estimates of π.
Stream<double> computePi({int batch: 100000}) async* {
var total = 0;
var count = 0;
while (true) {
final points = generateRandom().take(batch);
final inside = points.where((p) => p.isInsideUnitCircle);
total += batch;
count += inside.length;
final ratio = count / total;
// Area of a circle is A = π⋅r², therefore π = A/r².
// So, when given random points with x ∈ <0,1>,
// y ∈ <0,1>, the ratio of those inside a unit circle
// should approach π / 4. Therefore, the value of π
// should be:
yield ratio * 4;
}
}
Iterable<Point> generateRandom([int? seed]) sync* {
final random = Random(seed);
while (true) {
yield Point(random.nextDouble(), random.nextDouble());
}
}
class Point {
final double x, y;
const Point(this.x, this.y);
bool get isInsideUnitCircle => x * x + y * y <= 1;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment