1
0
Files
tmi-practicum-2018-2019/TMI-practicum/Program.cs
2019-05-24 09:55:39 +02:00

275 lines
9.5 KiB
C#
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
namespace TMI_practicum
{
internal static class Program
{
public static void Main(string[] args)
{
if (args.Length == 0 && !File.Exists("input.txt"))
{
Console.WriteLine("Please enter a file.");
Environment.Exit(1);
}
var inputFile = "input.txt";
if (args.Length != 0) inputFile = args[0];
if (!File.Exists(inputFile))
{
Console.WriteLine("File {0} not found.", inputFile);
Environment.Exit(1);
}
if (args.Length > 1) _outputFile = args[1];
(byte algorithm, _, IList<Circle> circles) = ParseFile(inputFile);
var stopwatch = new Stopwatch();
IEnumerable<Intersection> solved;
stopwatch.Start();
switch (algorithm)
{
case 1:
solved = SimpleAlgorithm.Solve(circles);
break;
case 2:
solved = SweepLineAlgorithm.Solve(circles);
break;
case 3:
solved = SweepLineEffAlgorithm.Solve(circles);
break;
default:
if (File.Exists(_outputFile))
{
File.Delete(_outputFile);
}
using (StreamWriter sw = File.CreateText(_outputFile))
{
sw.WriteLine("Dit algoritme is niet ge ̈ımplementeerd.");
}
throw new ArgumentException("Algorithm with id: " + algorithm + " is not defined!");
}
stopwatch.Stop();
WriteOutput(solved, stopwatch.ElapsedMilliseconds);
}
private static void CheckAlgo()
{
bool failed = false;
int i = 0;
while (!failed)
{
Console.WriteLine("start check {0}", i++);
var circles = CreateRandomCircles(5);
var correctSol = SweepLineAlgorithm.Solve(circles);
var solved = SweepLineEffAlgorithm.Solve(circles);
foreach (var intersection in correctSol)
{
if (solved.Contains(intersection)) continue;
if (solved.Contains(new Intersection(intersection.X + 1e-15, intersection.Y)) ||
solved.Contains(new Intersection(intersection.X - 1e-15, intersection.Y)) ||
solved.Contains(new Intersection(intersection.X + 1e-15, intersection.Y + 1e-15)) ||
solved.Contains(new Intersection(intersection.X + 1e-15, intersection.Y - 1e-15)) ||
solved.Contains(new Intersection(intersection.X - 1e-15, intersection.Y + 1e-15)) ||
solved.Contains(new Intersection(intersection.X - 1e-15, intersection.Y - 1e-15)) ||
solved.Contains(new Intersection(intersection.X, intersection.Y + 1e-15)) ||
solved.Contains(new Intersection(intersection.X, intersection.Y - 1e-15))
) continue;
bool found = solved.Any(ints =>
Math.Abs(ints.X - intersection.X) < 1e-12 && Math.Abs(ints.Y - intersection.Y) < 1e-12);
if (found) continue;
Console.WriteLine(InCircles(circles));
failed = true;
Console.WriteLine("Not found: {0}\t{1}", intersection.X, intersection.Y);
Console.WriteLine("correct");
foreach (var intersection1 in correctSol)
{
Console.WriteLine("{0}\t{1}", intersection1.X, intersection1.Y);
}
Console.WriteLine("wrong");
foreach (var intersection1 in solved)
{
Console.WriteLine("{0}\t{1}", intersection1.X, intersection1.Y);
}
Console.WriteLine("Cirkels");
foreach (var circle in circles)
{
Console.WriteLine("(x-{0})^2 + (y-{1})^2 = {2}^2", circle.X, circle.Y, circle.R);
}
foreach (var circle in circles)
{
Console.WriteLine("{0} {1} {2}", circle.X, circle.Y, circle.R);
}
break;
}
}
}
private static List<Circle> CreateRandomCircles(double amount)
{
var circles = new List<Circle>();
Random rnd = new Random();
for (int i = 0; i < amount; i++)
{
circles.Add(new Circle(Math.Round(rnd.NextDouble() * 1.0, 15), Math.Round(rnd.NextDouble() * 1.0, 15),
Math.Round(rnd.NextDouble() * (1.0 / amount), 15)));
}
return circles;
}
private static void GetChartData()
{
var stopwatch = new Stopwatch();
//warmup
var circles = CreateRandomCircles(20);
SweepLineEffAlgorithm.Solve(circles);
SweepLineAlgorithm.Solve(circles);
SimpleAlgorithm.Solve(circles);
var times = new Dictionary<string, List<long>>();
times.Add("algo1", new List<long>());
times.Add("algo2", new List<long>());
times.Add("algo3", new List<long>());
Console.WriteLine("size,\t algo1,\t algo2,\t algo3");
for (int s = 2; s < 300000; s *= 2)
{
for (int i = 0; i < 100; i++)
{
circles = CreateRandomCircles(s);
if (s < 50000)
{
stopwatch.Restart();
SimpleAlgorithm.Solve(circles);
stopwatch.Stop();
times["algo1"].Add(stopwatch.ElapsedMilliseconds);
} else times["algo1"].Add(0);
stopwatch.Restart();
SweepLineAlgorithm.Solve(circles);
stopwatch.Stop();
times["algo2"].Add(stopwatch.ElapsedMilliseconds);
stopwatch.Restart();
SweepLineEffAlgorithm.Solve(circles);
stopwatch.Stop();
times["algo3"].Add(stopwatch.ElapsedMilliseconds);
}
Console.WriteLine("{0},\t {1},\t {2},\t {3}", s, times["algo1"].Average(), times["algo2"].Average(), times["algo3"].Average());
times["algo1"].Clear();
times["algo2"].Clear();
times["algo3"].Clear();
}
stopwatch.Stop();
}
private static (byte Algorithm, int NbCircles, IList<Circle> Circles) ParseFile(string path)
{
byte algorithm = 0;
int nbCircles = 0;
Circle[] circles = null;
using (StreamReader file = new StreamReader(path))
{
try
{
algorithm = byte.Parse(file.ReadLine());
nbCircles = int.Parse(file.ReadLine());
circles = new Circle[nbCircles];
string line;
int i = 0;
while ((line = file.ReadLine()) != null)
{
double[] parts = line.Split(' ').Where(x => x.Length != 0).Select(double.Parse).ToArray();
if (parts.Length == 0) continue;
circles[i++] = new Circle(parts[0], parts[1], parts[2]);
}
}
catch (Exception)
{
Console.WriteLine("An error occured parsing the input file.\r\n" +
"Make sure the file has all required values and consists only of numbers.");
Environment.Exit(1);
}
}
return (algorithm, nbCircles, circles);
}
private static string _outputFile = "output.txt";
private static void WriteOutput(IEnumerable<Intersection> intersections, double time)
{
if (File.Exists(_outputFile))
{
File.Delete(_outputFile);
}
using (StreamWriter sw = File.CreateText(_outputFile))
{
foreach (Intersection intersection in intersections)
{
sw.WriteLine("{0:0.000000000000000}\t{1:0.000000000000000}", intersection.X, intersection.Y);
}
sw.WriteLine("\r\n{0}", time);
}
}
private static int InCircles(IList<Circle> circles)
{
int count = 0;
foreach (var toCheck in circles)
{
foreach (var circle in circles)
{
if (circle == toCheck) continue;
if (circle.R > toCheck.R && circle.Distance(toCheck) < circle.R &&
circle.FindIntersections(toCheck) == null)
{
count++;
}
}
}
return count;
}
}
}