diff --git a/2021/06/06.csproj b/2021/06/06.csproj
index 043826d..8af3444 100644
--- a/2021/06/06.csproj
+++ b/2021/06/06.csproj
@@ -8,4 +8,12 @@
enable
+
+
+ runtime; build; native; contentfiles; analyzers; buildtransitive
+ all
+
+
+
+
diff --git a/2021/06/Migrations/20211206123902_InitialCreate.Designer.cs b/2021/06/Migrations/20211206123902_InitialCreate.Designer.cs
new file mode 100644
index 0000000..51400dc
--- /dev/null
+++ b/2021/06/Migrations/20211206123902_InitialCreate.Designer.cs
@@ -0,0 +1,37 @@
+//
+using Day06;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Infrastructure;
+using Microsoft.EntityFrameworkCore.Migrations;
+using Microsoft.EntityFrameworkCore.Storage.ValueConversion;
+
+#nullable disable
+
+namespace _06.Migrations
+{
+ [DbContext(typeof(FishContext))]
+ [Migration("20211206123902_InitialCreate")]
+ partial class InitialCreate
+ {
+ protected override void BuildTargetModel(ModelBuilder modelBuilder)
+ {
+#pragma warning disable 612, 618
+ modelBuilder.HasAnnotation("ProductVersion", "6.0.0");
+
+ modelBuilder.Entity("Day06.Fish", b =>
+ {
+ b.Property("FishId")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("INTEGER");
+
+ b.Property("InternalTimer")
+ .HasColumnType("INTEGER");
+
+ b.HasKey("FishId");
+
+ b.ToTable("Fishes");
+ });
+#pragma warning restore 612, 618
+ }
+ }
+}
diff --git a/2021/06/Migrations/20211206123902_InitialCreate.cs b/2021/06/Migrations/20211206123902_InitialCreate.cs
new file mode 100644
index 0000000..b7c0eba
--- /dev/null
+++ b/2021/06/Migrations/20211206123902_InitialCreate.cs
@@ -0,0 +1,31 @@
+using Microsoft.EntityFrameworkCore.Migrations;
+
+#nullable disable
+
+namespace _06.Migrations
+{
+ public partial class InitialCreate : Migration
+ {
+ protected override void Up(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.CreateTable(
+ name: "Fishes",
+ columns: table => new
+ {
+ FishId = table.Column(type: "INTEGER", nullable: false)
+ .Annotation("Sqlite:Autoincrement", true),
+ InternalTimer = table.Column(type: "INTEGER", nullable: false)
+ },
+ constraints: table =>
+ {
+ table.PrimaryKey("PK_Fishes", x => x.FishId);
+ });
+ }
+
+ protected override void Down(MigrationBuilder migrationBuilder)
+ {
+ migrationBuilder.DropTable(
+ name: "Fishes");
+ }
+ }
+}
diff --git a/2021/06/Migrations/FishContextModelSnapshot.cs b/2021/06/Migrations/FishContextModelSnapshot.cs
new file mode 100644
index 0000000..015225e
--- /dev/null
+++ b/2021/06/Migrations/FishContextModelSnapshot.cs
@@ -0,0 +1,35 @@
+//
+using Day06;
+using Microsoft.EntityFrameworkCore;
+using Microsoft.EntityFrameworkCore.Infrastructure;
+using Microsoft.EntityFrameworkCore.Storage.ValueConversion;
+
+#nullable disable
+
+namespace _06.Migrations
+{
+ [DbContext(typeof(FishContext))]
+ partial class FishContextModelSnapshot : ModelSnapshot
+ {
+ protected override void BuildModel(ModelBuilder modelBuilder)
+ {
+#pragma warning disable 612, 618
+ modelBuilder.HasAnnotation("ProductVersion", "6.0.0");
+
+ modelBuilder.Entity("Day06.Fish", b =>
+ {
+ b.Property("FishId")
+ .ValueGeneratedOnAdd()
+ .HasColumnType("INTEGER");
+
+ b.Property("InternalTimer")
+ .HasColumnType("INTEGER");
+
+ b.HasKey("FishId");
+
+ b.ToTable("Fishes");
+ });
+#pragma warning restore 612, 618
+ }
+ }
+}
diff --git a/2021/06/Model.cs b/2021/06/Model.cs
new file mode 100644
index 0000000..d68cff8
--- /dev/null
+++ b/2021/06/Model.cs
@@ -0,0 +1,31 @@
+using System;
+using System.Collections.Generic;
+using Microsoft.EntityFrameworkCore;
+
+namespace Day06
+{
+ public class FishContext : DbContext
+ {
+ public DbSet Fishes { get; set; }
+
+ public string DbPath { get; }
+
+ public FishContext()
+ {
+ var folder = Environment.SpecialFolder.LocalApplicationData;
+ var path = Environment.GetFolderPath(folder);
+ DbPath = System.IO.Path.Join(path, "fishes.db");
+ }
+
+ // The following configures EF to create a Sqlite database file in the
+ // special "local" folder for your platform.
+ protected override void OnConfiguring(DbContextOptionsBuilder options)
+ => options.UseSqlite($"Data Source={DbPath}");
+ }
+
+ public class Fish
+ {
+ public int FishId { get; set; }
+ public int InternalTimer { get; set; }
+ }
+}
\ No newline at end of file
diff --git a/2021/06/Program.cs b/2021/06/Program.cs
index ebc65b5..65fd54e 100644
--- a/2021/06/Program.cs
+++ b/2021/06/Program.cs
@@ -23,18 +23,18 @@
Console.WriteLine($"Day: {currentDay} - there are {lanternFishPopulation.Count()} lantern fish");
for (int i = 0; i < lanternFishPopulation.Count; i++)
{
- switch(lanternFishPopulation[i])
+ switch (lanternFishPopulation[i])
{
- case 0:
- // its internal timer would reset to 6, and it would create a new lanternfish with an internal timer of 8.
- lanternFishPopulation[i] = 6;
- // Adding a new one with 9 though it should be 8 as this loop will catch new fish and decrement them. It's dirty, but fast way to solve the issue
- lanternFishPopulation.Add(9);
- break;
- default:
- // remove one day from the fish's countdown
- lanternFishPopulation[i] -= 1;
- break;
+ case 0:
+ // its internal timer would reset to 6, and it would create a new lanternfish with an internal timer of 8.
+ lanternFishPopulation[i] = 6;
+ // Adding a new one with 9 though it should be 8 as this loop will catch new fish and decrement them. It's dirty, but fast way to solve the issue
+ lanternFishPopulation.Add(9);
+ break;
+ default:
+ // remove one day from the fish's countdown
+ lanternFishPopulation[i] -= 1;
+ break;
}
}
@@ -42,6 +42,58 @@
}
}
+ static void SimulateLanternFishBigDatasets(ref List lanternFishPopulation, int daysToSimulate)
+ {
+ // A lanternfish that creates a new fish resets its timer to 6, not 7 (because 0 is included as a valid timer value). The new lanternfish starts with an internal timer of 8 and does not start counting down until the next day.
+
+ // Store dataset into db
+ using (var db = new FishContext())
+ {
+ foreach (var fish in lanternFishPopulation)
+ {
+ db.Add(new Fish { InternalTimer = fish });
+ db.SaveChanges();
+ }
+ }
+
+ int currentDay = 1;
+
+ while (currentDay <= daysToSimulate)
+ {
+ using (var db = new FishContext())
+ {
+ int fishCount = db.Fishes.Count();
+ Console.WriteLine($"Day: {currentDay} - there are {fishCount} lantern fish");
+
+ List fishIds = db.Fishes.Select(x => x.FishId).ToList();
+
+ foreach (int fishId in fishIds)
+ {
+ Fish fish = db.Fishes.First(x => x.FishId == fishId);
+
+ switch (fish.InternalTimer)
+ {
+ case 0:
+ // its internal timer would reset to 6, and it would create a new lanternfish with an internal timer of 8.
+ fish.InternalTimer = 6;
+ // Adding a new one with 9 though it should be 8 as this loop will catch new fish and decrement them. It's dirty, but fast way to solve the issue
+ db.Add(new Fish { InternalTimer = 9 });
+ break;
+ default:
+ // remove one day from the fish's countdown
+ fish.InternalTimer -= 1;
+ break;
+ }
+ }
+
+ db.SaveChanges();
+ }
+
+ currentDay += 1;
+ }
+ }
+
+
static void Part1(List lanternFish)
{
SimulateLanternFish(ref lanternFish, 80);
@@ -51,11 +103,16 @@
static void Part2(List lanternFish)
{
- SimulateLanternFish(ref lanternFish, 256);
+ SimulateLanternFishBigDatasets(ref lanternFish, 256);
// TODO - redo this using a database for large datasets, and entity framework, so as to avoid the HUGE memory usage
-
- Console.WriteLine($"After 256 days there are {lanternFish.Count()} lantern fish.");
+ using (var db = new FishContext())
+ {
+ int fishCount = db.Fishes.Count();
+ Console.WriteLine($"After 256 days there are {fishCount} lantern fish.");
+ }
+
+
}
}
}
\ No newline at end of file
diff --git a/2021/06/readme.md b/2021/06/readme.md
new file mode 100644
index 0000000..cf5d3eb
--- /dev/null
+++ b/2021/06/readme.md
@@ -0,0 +1,3 @@
+Run dotnet ef database update to initialise the database
+Delete the database if you want to run the code again
+It's at C:\Users\Josh\AppData\Local as fishes.db and other associated files
\ No newline at end of file