From 4dcdadceaca2d21901ec0cde531adbc7e3efe827 Mon Sep 17 00:00:00 2001 From: jrtechs Date: Sun, 11 Nov 2018 21:38:40 -0500 Subject: [PATCH 01/59] Started working on paragraph formatter. --- other/paragraphFormatting.py | 98 ++++++++++++++++++++++++++++++++++++ 1 file changed, 98 insertions(+) create mode 100644 other/paragraphFormatting.py diff --git a/other/paragraphFormatting.py b/other/paragraphFormatting.py new file mode 100644 index 0000000..0e6b745 --- /dev/null +++ b/other/paragraphFormatting.py @@ -0,0 +1,98 @@ + +def extraSpace(S, M, i, j): + """ + Computes the number of extra characters at the end of + the line. + Between each word there is only once space. + + :param S: List of words + :param M: Max length of line + :param i: start word index + :param j: end word index + """ + extraSpaces = M - j + i + for x in range(i, j + 1): + extraSpaces -= len(S[x]) + return extraSpaces + + +def badnessLine(S, M, i, j): + """ + Computes Line badness. This is the number of + extra spaces or infinity if the length exceeds M + + :param S: List of words + :param M: Max length of line + :param i: start word index + :param j: end word index + """ + es = extraSpace(S, M, i, j) + if es < 0: + return float("infinity") + return es + + +def minBad(S, M, i): + """ + Computes the badness of a paragraph as the + badness of the worst line in the paragraph not + including the last line. + + *this is recursive + + :param S: List of words + :param M: Max length of line + :param i: start word index + """ + if len(S) == 0: + return 0 + + # Calculate the current line's badness + curBad = 0 + + k = i + while curBad > badnessLine(S, M, i, k): + curBad = badnessLine(S, M, i, k) + k = k + 1 + + return max(curBad, badnessLine(S, M, k)) + + + +def minBadDynamic(S, M): + """ + Write a procedure minBadDynamic that implements + the function mb' using dynamic program- + ming. It should take only two parameters: S and M + + :param S: List of words + :param M: Max length of line + """ + pass + + +def minBadDynamicChoice(S, M): + """ + Write a procedure minBadDynamicChoice that implements + the function mb 0 using dynamic + programming. In addition to returning mb(S, M ), it + should also return the choices made + + :param S: List of words + :param M: Max length of line + """ + pass + + +def printParagraph(S, M): + """ + which takes two parameters: S and M that displays the words in S on + the screen using the choices of minBadDynamicChoice. + + What is the asymptotic running time of your + algorithm? + + :param S: List of words + :param M: Max length of line + """ + pass From a053d0213d65613e78f10334b0729d541ecf81dc Mon Sep 17 00:00:00 2001 From: jrtechs Date: Mon, 12 Nov 2018 17:29:13 -0500 Subject: [PATCH 02/59] Updated the matrix chain problem to backtrack and print the solution. --- other/minMul.py | 17 ++++++++++++++--- 1 file changed, 14 insertions(+), 3 deletions(-) diff --git a/other/minMul.py b/other/minMul.py index a2434c1..5cfbbc4 100644 --- a/other/minMul.py +++ b/other/minMul.py @@ -6,6 +6,13 @@ Jeffery Russell """ +def generateMinOrdering(C, i, j): + if i == j: + return str(i) + return "(" + generateMinOrdering(C, i, C[i -1][j -1]) + generateMinOrdering(C, C[i -1][ j -1] +1, j) + ")" + + + def minMul(S): """ Simple function to print the matrixes used in @@ -41,7 +48,10 @@ def minMul(S): for i in range(0, n): for y in range(0, n): print(str(c[i][y]) + " ", end =" ") - print() + print() + + print(generateMinOrdering(c, 1, len(S))) + """ @@ -49,7 +59,8 @@ Makes sure that other programs don't execute the main """ if __name__ == '__main__': try: - minMul([(10,100),(100, 5),(5, 50)]) - #minMul([(5,10),(10,3),(3,12), (12,5), (5,50), (50,6)]) + #minMul([(10,100),(100, 5),(5, 50)]) + minMul([(5,10),(10,3),(3,12), (12,5), (5,50), (50,6)]) + #minMul([(30,35),(35,15),(15,5), (5,10), (10,20), (20,25)]) except KeyboardInterrupt: exit() \ No newline at end of file From 3fbc19d8d506976e8d8a669219ff6241bc4ea6e6 Mon Sep 17 00:00:00 2001 From: jrtechs Date: Wed, 14 Nov 2018 07:52:36 -0500 Subject: [PATCH 03/59] Designed a dynamic programming technique for the paragraph formatter. --- other/paragraphFormatting.py | 94 ++++++++++++++++++++++++++++++------ 1 file changed, 79 insertions(+), 15 deletions(-) diff --git a/other/paragraphFormatting.py b/other/paragraphFormatting.py index 0e6b745..41bfa38 100644 --- a/other/paragraphFormatting.py +++ b/other/paragraphFormatting.py @@ -1,3 +1,10 @@ +import math + +""" +Jeffery Russell +11-13-18 +""" + def extraSpace(S, M, i, j): """ @@ -28,7 +35,7 @@ def badnessLine(S, M, i, j): """ es = extraSpace(S, M, i, j) if es < 0: - return float("infinity") + return math.inf return es @@ -44,19 +51,17 @@ def minBad(S, M, i): :param M: Max length of line :param i: start word index """ - if len(S) == 0: + if badnessLine(S, M, i, len(S) -1) != math.inf: return 0 - # Calculate the current line's badness - curBad = 0 - - k = i - while curBad > badnessLine(S, M, i, k): - curBad = badnessLine(S, M, i, k) - k = k + 1 - - return max(curBad, badnessLine(S, M, k)) + min = math.inf + for k in range(i + 1, len(S)): + end = minBad(S, M, k) + front = badnessLine(S, M, i, k - 1) + max = end if end > front else front + min = min if min < max else max + return min def minBadDynamic(S, M): @@ -68,20 +73,63 @@ def minBadDynamic(S, M): :param S: List of words :param M: Max length of line """ - pass + cost = [math.inf for i in range(len(S))] + + for i in range(0, len(S)): + if badnessLine(S, M, 0, i) != math.inf: + cost[i] = badnessLine(S, M, 0, i) + if i == len(S) -1: + return 0 #Everything fit on one line + else: + min = math.inf + for k in range(0, i): + before = cost[k] + after = badnessLine(S, M, k + 1, i) + if i == len(S) -1 and badnessLine(S, M, k+1, i) != math.inf: + after = 0 # Last Line + max = before if before > after else after + min = min if min < max else max + cost[i] = min + return cost[len(S) -1] def minBadDynamicChoice(S, M): """ Write a procedure minBadDynamicChoice that implements - the function mb 0 using dynamic + the function mb' using dynamic programming. In addition to returning mb(S, M ), it should also return the choices made :param S: List of words :param M: Max length of line """ - pass + cost = [math.inf for i in range(len(S))] + + # List of tuples indicating start/end indices of line + choice = [[] for i in range(len(S))] + + for i in range(0, len(S)): + if badnessLine(S, M, 0, i) != math.inf: + cost[i] = badnessLine(S, M, 0, i) + choice[i] = [(0, i)] + if i == len(S) - 1: + return 0, [(0,i)] # One line + else: + min = math.inf + choiceCanidate = [] + for k in range(0, i): # Finds the optimal solution + before = cost[k] # Previously computed minimum + after = badnessLine(S, M, k + 1, i) # Badness of new slice + if i == len(S) - 1 and badnessLine(S, M, k+1, i) != math.inf: + after = 0 # Last line + max = before if before > after else after + if min > max: + # Captures where slice is being taken + choiceCanidate = choice[k] + [(k+1, i)] + min = max + choice[i] = choiceCanidate + cost[i] = min + return cost[len(S) -1], choice[len(S) -1] def printParagraph(S, M): @@ -92,7 +140,23 @@ def printParagraph(S, M): What is the asymptotic running time of your algorithm? + This program will run asymptotically in O(n^2) due + to the characteristic of calculating the minBad + for each sub sequence and then looping through a + maximum of |S| to find the optimal solution. + :param S: List of words :param M: Max length of line """ - pass + cost, choice = minBadDynamicChoice(S, M) + print() + for i in range(0, len(choice)): + for x in range(choice[i][0], choice[i][1] + 1): + print(str(S[x]), end=" ") + print() + + +print(minBadDynamicChoice(["aaa", "aaa"], 6)) +printParagraph(["jjjjjj","aaa", "bb", "cc", "ff", "mm", "ddddd", "ddddd"], 6) + +printParagraph(["jjjjjj"], 6) \ No newline at end of file From 2f8d25877d715faabe4c28e3421903719fa10efd Mon Sep 17 00:00:00 2001 From: jrtechs Date: Tue, 27 Nov 2018 11:31:53 -0500 Subject: [PATCH 04/59] Created simple program to backup windows sticky notes. --- windows/Sticky Notes Backuper/Readme.txt | 14 ++++++++++++++ windows/Sticky Notes Backuper/grabStickyNotes.bat | 9 +++++++++ .../replaceCurrentStickyNotes.bat | 9 +++++++++ 3 files changed, 32 insertions(+) create mode 100644 windows/Sticky Notes Backuper/Readme.txt create mode 100644 windows/Sticky Notes Backuper/grabStickyNotes.bat create mode 100644 windows/Sticky Notes Backuper/replaceCurrentStickyNotes.bat diff --git a/windows/Sticky Notes Backuper/Readme.txt b/windows/Sticky Notes Backuper/Readme.txt new file mode 100644 index 0000000..d0781e5 --- /dev/null +++ b/windows/Sticky Notes Backuper/Readme.txt @@ -0,0 +1,14 @@ +This is a very simple program. + +Double click on grab StickyNotes.bat to backup your sticky notes +into the current directory. + +Double click ReplaceCurrentStickyNotes.bat to replace your +stickynotes with the ones in the current directory. + + + + +** Note this will only work with windows 10 and up. +Windows 10 uses the .sqlite format where windows 7 +used a .snt file. \ No newline at end of file diff --git a/windows/Sticky Notes Backuper/grabStickyNotes.bat b/windows/Sticky Notes Backuper/grabStickyNotes.bat new file mode 100644 index 0000000..14dcf4b --- /dev/null +++ b/windows/Sticky Notes Backuper/grabStickyNotes.bat @@ -0,0 +1,9 @@ +:: Author : Jeffery Russell 11-27-18 + +@echo off + +pushd %~dp0 +dir +copy %LocalAppData%\Packages\Microsoft.MicrosoftStickyNotes_8wekyb3d8bbwe\LocalState\plum.sqlite + +pause \ No newline at end of file diff --git a/windows/Sticky Notes Backuper/replaceCurrentStickyNotes.bat b/windows/Sticky Notes Backuper/replaceCurrentStickyNotes.bat new file mode 100644 index 0000000..22df29d --- /dev/null +++ b/windows/Sticky Notes Backuper/replaceCurrentStickyNotes.bat @@ -0,0 +1,9 @@ +:: Author : Jeffery Russell 11-27-18 + +@echo off + +pushd %~dp0 +dir +copy plum.sqlite %LocalAppData%\Packages\Microsoft.MicrosoftStickyNotes_8wekyb3d8bbwe\LocalState\plum.sqlite + +pause \ No newline at end of file From 5129e5e13321b6d78d475a3afd254f87134223ef Mon Sep 17 00:00:00 2001 From: jrtechs Date: Fri, 11 Jan 2019 13:55:20 -0500 Subject: [PATCH 05/59] Python implementation of the knapsack problem. --- other/knapSack.py | 52 +++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 52 insertions(+) create mode 100644 other/knapSack.py diff --git a/other/knapSack.py b/other/knapSack.py new file mode 100644 index 0000000..4bfdece --- /dev/null +++ b/other/knapSack.py @@ -0,0 +1,52 @@ +""" +Jeffery Russell +12-1-18 +""" + + +def knapsack(V, W, capacity): + """ + Dynamic programming implementation of the knapsack problem + + :param V: List of the values + :param W: List of weights + :param capacity: max capacity of knapsack + :return: List of tuples of objects stolen in form (w, v) + """ + choices = [[[] for i in range(capacity + 1)] for j in range(len(V) + 1)] + cost = [[0 for i in range(capacity + 1)] for j in range(len(V) + 1)] + + for i in range(0, len(V)): + for j in range(0, capacity + 1): + if W[i] > j: # don't include another item + cost[i][j] = cost[i -1][j] + choices[i][j] = choices[i - 1][j] + else: # Adding another item + cost[i][j] = max(cost[i-1][j], cost[i-1][j - W[i]] + V[i]) + if cost[i][j] != cost[i-1][j]: + choices[i][j] = choices[i - 1][j - W[i]] + [(W[i], V[i])] + else: + choices[i][j] = choices[i - 1][j] + return choices[len(V) -1][capacity] + + +def printSolution(S): + """ + Takes the output of knapsack and prints it in a + pretty format. + + :param S: list of tuples representing items stolen + :return: None + """ + print("Thief Took:") + for i in S: + print("Weight: " + str(i[0]) + "\tValue: \t" + str(i[1])) + + print() + print("Total Value Stolen: " + str(sum(int(v[0]) for v in S))) + print("Total Weight in knapsack: " + str(sum(int(v[1]) for v in S))) + + +values = [99,1,1,1,1, 1,1] +weights = [5,1,2,3,4,5,1] +printSolution(knapsack(values, weights, 6)) \ No newline at end of file From dcfe1999826d69f9011848d3c6758be33c2218ab Mon Sep 17 00:00:00 2001 From: jrtechs Date: Sun, 20 Jan 2019 20:06:45 -0500 Subject: [PATCH 06/59] Created simple web page which prompts user to load a JSON file and it graphs it using visjs. --- graphing/basicGraph.html | 92 ++++++++++++++++++++++++++++++++++++++++ graphing/ex.json | 1 + 2 files changed, 93 insertions(+) create mode 100644 graphing/basicGraph.html create mode 100644 graphing/ex.json diff --git a/graphing/basicGraph.html b/graphing/basicGraph.html new file mode 100644 index 0000000..e75c3fc --- /dev/null +++ b/graphing/basicGraph.html @@ -0,0 +1,92 @@ + + + + Graph2d | Performance + + + + + + + + + + + + +
+ +Click the button then choose a file to graph. + +

+
+
+
+
+ +
+ + + diff --git a/graphing/ex.json b/graphing/ex.json new file mode 100644 index 0000000..6615c8e --- /dev/null +++ b/graphing/ex.json @@ -0,0 +1 @@ +[{"x": "2014-06-1", "y": -6},{"x": "2014-06-11", "y": 0},{"x": "2014-06-12", "y": 25},{"x": "2014-06-13", "y": 30},{"x": "2014-06-14", "y": 10},{"x": "2014-06-15", "y": 15},{"x": "2014-06-16", "y": 30}] From 72e484e046a4ee955016cf5a937a95d5b232c581 Mon Sep 17 00:00:00 2001 From: jrtechs Date: Tue, 29 Jan 2019 20:53:13 -0500 Subject: [PATCH 07/59] Created some basic framework classes to use for my testing of multi threaded file io. --- multiThreadedFileIO/FileReader.java | 44 ++++++++++++++++ multiThreadedFileIO/ReadTask.java | 20 ++++++++ multiThreadedFileIO/TaskManager.java | 76 ++++++++++++++++++++++++++++ 3 files changed, 140 insertions(+) create mode 100644 multiThreadedFileIO/FileReader.java create mode 100644 multiThreadedFileIO/ReadTask.java create mode 100644 multiThreadedFileIO/TaskManager.java diff --git a/multiThreadedFileIO/FileReader.java b/multiThreadedFileIO/FileReader.java new file mode 100644 index 0000000..520fa81 --- /dev/null +++ b/multiThreadedFileIO/FileReader.java @@ -0,0 +1,44 @@ +import java.io.BufferedReader; +import java.io.FileInputStream; +import java.io.IOException; +import java.io.InputStreamReader; + + +/** + * Simple class for reading files as strings. + * + * @author Jeffery Russell + */ +public class FileReader +{ + + public static String readFile(String filePath) + { + String fileContent = new String(); + + try + { + BufferedReader br = new BufferedReader( + new InputStreamReader(new FileInputStream(filePath))); + String line; + + while ((line = br.readLine()) != null) + { + fileContent = fileContent.concat(line); + } + br.close(); + } + catch (IOException e) + { + e.printStackTrace(); + } + return fileContent; + } + + + public static void main(String[] args) + { + System.out.println("Test"); + System.out.println(FileReader.readFile("./testData/data1.txt")); + } +} \ No newline at end of file diff --git a/multiThreadedFileIO/ReadTask.java b/multiThreadedFileIO/ReadTask.java new file mode 100644 index 0000000..249f608 --- /dev/null +++ b/multiThreadedFileIO/ReadTask.java @@ -0,0 +1,20 @@ +/** + * Simple method to be used by the task manager to do + * file io. + * + * @author Jeffery Russell + */ +public class ReadTask +{ + private String fileName; + + public ReadTask(String fileName) + { + this.fileName = fileName; + } + + public void runTask() + { + FileReader.readFile(fileName); + } +} \ No newline at end of file diff --git a/multiThreadedFileIO/TaskManager.java b/multiThreadedFileIO/TaskManager.java new file mode 100644 index 0000000..63b5ce1 --- /dev/null +++ b/multiThreadedFileIO/TaskManager.java @@ -0,0 +1,76 @@ +import java.util.List; +import java.util.Vector; + +/** + * A class which enables user to run a large chunk of + * tasks in parallel efficiently. + * + * @author Jeffery 1-29-19 + */ +public class TaskManager +{ + /** Number of threads to use at once */ + private int threadCount; + + /** Meaningless tasks to run in parallel */ + private List tasks; + + + public TaskManager(int threadCount) + { + this.threadCount = threadCount; + //using vectors because they are thread safe + this.tasks = new Vector<>(); + } + + + public void addTask(ReadTask t) + { + tasks.add(t); + } + + + /** + * This is the fun method. + * + * This will run all of the tasks in parallel using the + * desired amount of threads untill all of the jobs are + * complete. + */ + public void runTasks() + { + int desiredThreads = threadCount > tasks.size() ? + tasks.size() : threadCount; + + Thread[] runners = new Thread[desiredThreads]; + + System.out.println("Total Tasks: " + tasks.size()); + System.out.println("Threads Used:" + desiredThreads); + + + for(int i = 0; i < desiredThreads; i++) + { + runners[i] = new Thread(()-> + { + while(!tasks.isEmpty()) + { + ReadTask t = tasks.remove(0); + t.runTask(); + } + }); + runners[i].start(); + } + + for(int i = 0; i < desiredThreads; i++) + { + try + { + runners[i].join(); + } + catch (Exception e) + { + e.printStackTrace(); + } + } + } +} \ No newline at end of file From f1ae532387d33e2693675d8b8cde6239820b6742 Mon Sep 17 00:00:00 2001 From: jrtechs Date: Thu, 31 Jan 2019 13:12:36 -0500 Subject: [PATCH 08/59] Wrote tests to compare the read time of files vs number of cpu threads used. --- multiThreadedFileIO/DataCreator.java | 71 +++++++++++++++++++ .../MultiThreadedFileReadTest.java | 40 +++++++++++ multiThreadedFileIO/TaskManager.java | 25 +++++-- multiThreadedFileIO/graph.py | 13 ++++ 4 files changed, 142 insertions(+), 7 deletions(-) create mode 100644 multiThreadedFileIO/DataCreator.java create mode 100644 multiThreadedFileIO/MultiThreadedFileReadTest.java create mode 100644 multiThreadedFileIO/graph.py diff --git a/multiThreadedFileIO/DataCreator.java b/multiThreadedFileIO/DataCreator.java new file mode 100644 index 0000000..e551be1 --- /dev/null +++ b/multiThreadedFileIO/DataCreator.java @@ -0,0 +1,71 @@ +import java.io.BufferedWriter; +import java.io.File; +import java.io.FileWriter; +import java.math.*; + +/** + * Simple class to generate random data for + * file IO tests. + * + * @author Jeffery Russell 1-31-19 + */ +public class DataCreator +{ + /** + * Generates an obscure random character + * @return + */ + private static char rndChar() + { + // or use Random or whatever + int rnd = (int) (Math.random() * 52); + char base = (rnd < 26) ? 'A' : 'a'; + return (char) (base + rnd % 26); + } + + + /** + * Simple function to save contents to the disk + * + * @param s + * @param fileName + */ + private static void saveToDisk(String s, String fileName) + { + BufferedWriter writer; + try + { + File file = new File(fileName); + file.createNewFile(); + writer = new BufferedWriter(new FileWriter(file)); + writer.write(s); + writer.flush(); + writer.close(); + } + catch (Exception e) + { + e.printStackTrace(); + } + } + + + /** + * Creates 5MB of random test data to use + */ + public static void main(String[] arguments) + { + System.out.println("Creating Test Files"); + for(int i = 0; i < 100; i++) + { + //10k random characters for each file + //each file is 10kb * 500 files, total size of 5MB + String s = ""; + for(int j = 0; j < 1000000; j++) + { + s = s + rndChar(); + } + saveToDisk(s, "./testData/" + i + ".txt"); + System.out.println(s); + } + } +} \ No newline at end of file diff --git a/multiThreadedFileIO/MultiThreadedFileReadTest.java b/multiThreadedFileIO/MultiThreadedFileReadTest.java new file mode 100644 index 0000000..32c63df --- /dev/null +++ b/multiThreadedFileIO/MultiThreadedFileReadTest.java @@ -0,0 +1,40 @@ +import java.util.*; + +/** + * File to test the performance of multi threaded file + * io by reading a large quantity of files in parallel + * using a different amount of threads. + * + * @author Jeffery Russell 1-31-19 + */ +public class MultiThreadedFileReadTest +{ + public static void main(String[] args) + { + List x = new ArrayList<>(); + List y = new ArrayList<>(); + for(int i = 1; i <= 64; i++) + { + long threadTotal = 0; + for(int w = 0; w < 20; w++) + { + TaskManager boss = new TaskManager(i); + + for(int j = 0; j < 500; j++) + { + boss.addTask(new ReadTask("./testData/" + i + ".txt")); + } + long startTime = System.nanoTime(); + boss.runTasks(); + long endTime = System.nanoTime(); + long durationMS = (endTime - startTime)/1000000; + threadTotal+= durationMS; + } + + x.add(i); + y.add(threadTotal/20.0); //finds average + } + System.out.println(x); + System.out.println(y); + } +} \ No newline at end of file diff --git a/multiThreadedFileIO/TaskManager.java b/multiThreadedFileIO/TaskManager.java index 63b5ce1..2929b31 100644 --- a/multiThreadedFileIO/TaskManager.java +++ b/multiThreadedFileIO/TaskManager.java @@ -44,18 +44,29 @@ public class TaskManager Thread[] runners = new Thread[desiredThreads]; - System.out.println("Total Tasks: " + tasks.size()); - System.out.println("Threads Used:" + desiredThreads); - - for(int i = 0; i < desiredThreads; i++) { runners[i] = new Thread(()-> { - while(!tasks.isEmpty()) + ReadTask t = null; + while(true) { - ReadTask t = tasks.remove(0); - t.runTask(); + //need synchronized block to prevent + //race condition + synchronized (tasks) + { + if(!tasks.isEmpty()) + t = tasks.remove(0); + } + if(t == null) + { + break; + } + else + { + t.runTask(); + t = null; + } } }); runners[i].start(); diff --git a/multiThreadedFileIO/graph.py b/multiThreadedFileIO/graph.py new file mode 100644 index 0000000..469f90b --- /dev/null +++ b/multiThreadedFileIO/graph.py @@ -0,0 +1,13 @@ +import matplotlib.pyplot as plt + + +xList = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63, 64] +yList = [230.5, 124.0, 84.65, 63.9, 51.6, 44.2, 39.15, 34.9, 31.9, 28.7, 27.2, 25.05, 24.25, 22.8, 21.25, 20.45, 19.8, 19.4, 18.6, 17.45, 17.0, 16.95, 16.4, 24.15, 15.2, 15.2, 15.0, 14.3, 14.7, 14.65, 14.65, 14.75, 13.85, 15.1, 14.35, 35.75, 15.3, 14.45, 14.25, 13.65, 14.45, 14.6, 13.95, 14.65, 14.5, 14.3, 14.85, 14.15, 15.0, 16.25, 14.25, 14.4, 14.15, 14.45, 14.25, 14.85, 14.3, 14.35, 15.35, 13.6, 14.3, 14.2, 14.3, 13.95] + + + +plt.plot(xList, yList) +plt.xlabel('Number of Threads') +plt.ylabel('Execution Time (MS)') + +plt.show() \ No newline at end of file From 43a19cf3f9c8dd3006b6112a1eb6239f3e660f2d Mon Sep 17 00:00:00 2001 From: jrtechs Date: Fri, 22 Feb 2019 21:45:03 -0500 Subject: [PATCH 09/59] Started working on genetic algorithm in javascript. --- geneticAlgorithm/geneticAlgo.html | 104 ++++++++++++++++++++++++++++++ 1 file changed, 104 insertions(+) create mode 100644 geneticAlgorithm/geneticAlgo.html diff --git a/geneticAlgorithm/geneticAlgo.html b/geneticAlgorithm/geneticAlgo.html new file mode 100644 index 0000000..cdbd682 --- /dev/null +++ b/geneticAlgorithm/geneticAlgo.html @@ -0,0 +1,104 @@ + + + + + + + + + + + + + \ No newline at end of file From 98bd2dd1c4643b0e9c5b5d6a41c35a5da18c49ff Mon Sep 17 00:00:00 2001 From: jrtechs Date: Sat, 23 Feb 2019 10:36:19 -0500 Subject: [PATCH 10/59] Finished writing the genetic algorithm. --- geneticAlgorithm/geneticAlgo.html | 178 +++++++++++++++++++++++++++--- 1 file changed, 164 insertions(+), 14 deletions(-) diff --git a/geneticAlgorithm/geneticAlgo.html b/geneticAlgorithm/geneticAlgo.html index cdbd682..a79839b 100644 --- a/geneticAlgorithm/geneticAlgo.html +++ b/geneticAlgorithm/geneticAlgo.html @@ -1,8 +1,6 @@ - + let exampleOrganism = new Chromosome(geneList); + runGeneticOptimization(exampleOrganism, basicCostFunction, 100, 50, 0.01, 0.3, 20, 10); + + From 4376164ab8b22bfba22826e4c9384e1f274768e9 Mon Sep 17 00:00:00 2001 From: jrtechs Date: Sat, 23 Feb 2019 13:06:36 -0500 Subject: [PATCH 11/59] Created plotting graph for the genetic algorithm. --- geneticAlgorithm/geneticAlgo.html | 185 +++++++++++++++++++++++++++++- 1 file changed, 182 insertions(+), 3 deletions(-) diff --git a/geneticAlgorithm/geneticAlgo.html b/geneticAlgorithm/geneticAlgo.html index a79839b..8d9c8d8 100644 --- a/geneticAlgorithm/geneticAlgo.html +++ b/geneticAlgorithm/geneticAlgo.html @@ -1,5 +1,14 @@ + + + + + + +
+ + + + +
+
+

Population Variables

+
+
+
+
+ + +
+
+ + +
+
+
+
+ + +
+
+ + +
+
+
+ +
+
+ From 9f0bf214b980af65a915c966ba44d683f43e59fc Mon Sep 17 00:00:00 2001 From: jrtechs Date: Sat, 23 Feb 2019 14:03:26 -0500 Subject: [PATCH 12/59] Added a line chart displaying the average cost and best cost. --- geneticAlgorithm/geneticAlgo.html | 112 ++++++++++++++++++++++-------- 1 file changed, 83 insertions(+), 29 deletions(-) diff --git a/geneticAlgorithm/geneticAlgo.html b/geneticAlgorithm/geneticAlgo.html index 8d9c8d8..e8f31d9 100644 --- a/geneticAlgorithm/geneticAlgo.html +++ b/geneticAlgorithm/geneticAlgo.html @@ -114,11 +114,13 @@ const naturalSelection = function(population, keepNumber, fitnessFunction) { let fitnessArray = []; + let total = 0; for(let i = 0; i < population.length; i++) { const fitness = fitnessFunction(population[i]); console.log(fitness); fitnessArray.push({fit:fitness, chrom: population[i]}); + total+= fitness; } fitnessArray.sort(predicateBy("fit")); @@ -130,7 +132,7 @@ { survivors.push(fitnessArray[i].chrom); } - return {survivors: survivors, bestFit: bestFitness, bestChrom: bestChromosome}; + return {average: total/population.length, survivors: survivors, bestFit: bestFitness, bestChrom: bestChromosome}; }; const blendGene = function(gene1, gene2, blendCoef) @@ -254,12 +256,10 @@ bestCostG = Number.MAX_VALUE, bestChromosomeG = genericChromosomeG; const runGeneticOptimizationforGraph = function() { - - - - let generationResult = naturalSelection(populationG, keepNumberG, costFunctionG); + stats.push([generationG, generationResult.bestFit, generationResult.average]); + if(bestCostG > generationResult.bestFit) { bestChromosomeG = generationResult.bestChrom; @@ -269,7 +269,6 @@ generationG++; - console.log("Generation " + generationG + " Best Cost: " + bestCostG); console.log(generationResult); @@ -279,12 +278,13 @@ mutatePopulation(populationG, mutationRateG); createGraph(); - }; + + let stats = []; const createGraph = function() { - var dataPoints = []; + var dataPoints = []; console.log(dataPoints); @@ -307,6 +307,29 @@ var chart = new google.visualization.ScatterChart(document.getElementById('chart_div')); chart.draw(data, options); + + //line chart stuff + var line_data = new google.visualization.DataTable(); + line_data.addColumn('number', 'Generation'); + line_data.addColumn('number', 'Best'); + line_data.addColumn('number', 'Average'); + + line_data.addRows(stats); + + console.log(stats); + + var lineChartOptions = { + hAxis: { + title: 'Generation' + }, + vAxis: { + title: 'Cost' + }, + colors: ['#AB0D06', '#007329'] + }; + + var chart = new google.visualization.LineChart(document.getElementById('line_chart')); + chart.draw(line_data, lineChartOptions); }; @@ -328,31 +351,63 @@ generationG = 0; - function resetPopulation() + function verifyForm() { + if(Number($("#populationSize").val()) <= 1) + { + alert("Population size must be greater than one."); + return false; + } + + if(Number($("#mutationRate").val()) > 1 || + Number($("#mutationRate").val()) < 0) + { + alert("Mutation rate must be between zero and one."); + return false; + } - autoRunning = false; - $("#runAutoOptimizer").val("Auto Run"); + if(Number($("#survivalSize").val()) < 0) + { + alert("Survival size can't be less than one."); + return false; + } + + if(Number($("#newBlood").val()) < 0) + { + alert("New organisms can't be a negative number."); + return false; + } + return true; + } - populationSizeG = $("#populationSize").val(); - mutationRateG = $("#mutationRate").val(); - keepNumberG = $("#survivalSize").val(); - newBloodNumberG = $("#newBlood").val(); - generationG = 0; + function resetPopulation() + { + if(verifyForm()) + { + stats = []; + autoRunning = false; + $("#runAutoOptimizer").val("Auto Run"); - populationG = createRandomPopulation(genericChromosomeG, populationSizeG); - createGraph(); + populationSizeG = $("#populationSize").val(); + mutationRateG = $("#mutationRate").val(); + keepNumberG = $("#survivalSize").val(); + newBloodNumberG = $("#newBlood").val(); + generationG = 0; + + populationG = createRandomPopulation(genericChromosomeG, populationSizeG); + createGraph(); + } } populationG = createRandomPopulation(genericChromosomeG, populationSizeG); - window.onload = function () { + window.onload = function (){ + google.charts.load('current', {packages: ['corechart', 'line']}); google.charts.load('current', {'packages':['corechart']}).then(function() { createGraph(); }) - }; @@ -382,8 +437,6 @@ runAutoOptimizer(); } - - //runGeneticOptimization(exampleOrganism, basicCostFunction, 100, 50, 0.01, 0.3, 20, 10); @@ -394,6 +447,8 @@
+
+ @@ -401,32 +456,31 @@

Population Variables

-
+
- +
- +
- +
- +

-
+ - From e5e809a58d840c96a7dd2162178bee1d2554c75d Mon Sep 17 00:00:00 2001 From: jrtechs Date: Thu, 18 Apr 2019 19:43:12 -0400 Subject: [PATCH 13/59] Added vim configuration file to repository. --- config/vimrc | 120 +++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 120 insertions(+) create mode 100644 config/vimrc diff --git a/config/vimrc b/config/vimrc new file mode 100644 index 0000000..9f9f3d2 --- /dev/null +++ b/config/vimrc @@ -0,0 +1,120 @@ +" sets spell check to be enabled to files which +" end with either .md or .txt +" +" To get auto complete type z= when you are +" over the word. +autocmd BufRead,BufNewFile *.md setlocal spell spelllang=en_us +autocmd BufRead,BufNewFile *.txt setlocal spell spelllang=en_us + + +""" Indentation and Tabs """ +"file based indentation +filetype plugin indent on + +"copy indentation from current line when making a new line +set autoindent +" Smart indentation when programming: indent after { +set smartindent + +set tabstop=4 " number of spaces per tab +set expandtab " convert tabs to spaces +set shiftwidth=4 " set a tab press equal to 4 spaces + + +""" Looks and Appearance""" + +" Enable syntax highlighting +syntax enable + +" Enable 256 colors palette in Gnome Terminal +if $COLORTERM == 'gnome-terminal' + set t_Co=256 +endif + +try + colorscheme desert +catch +endtry + +set background=dark + +" Set extra options when running in GUI mode +if has("gui_running") + set guioptions-=T + set guioptions-=e + set t_Co=256 + set guitablabel=%M\ %t +endif + + +" File Encodings + +" Set utf8 as standard encoding and en_US as the standard language +set encoding=utf8 + +" Use Unix as the standard file type +set ffs=unix,dos,mac + + +" Productivity + +" Set Line Numbers to show +set number + +" Highlights the current line with a underscore +set cursorline + +" Displays a red bar at 80 characters +set colorcolumn=80 + +" Shows a auto complete tab when you are typing a command +" like :sp +set wildmenu + +" sets the size of the status bar at bottom to have a height of two +set laststatus=2 + + + +" Searching when in command mode type /words to find +" search as characters are entered +set incsearch +" highlight matched characters +set hlsearch + +" Ignore case when searching +set ignorecase + + + +"Disable ding sound on error, flashes cursor instead +set visualbell + +" Display ruler on bottom right -- should be there by default +set ruler + +" Enables mouse support +set mouse=a + +" Auto updates file if an external source edits the file +set autoread + +" Improves performance by only redrawing screen when needed +set lazyredraw + + +" Copy and paste +" Selection +" v and arrows select characters +" V select entire lines +" d on something selected cuts it -- also used for delete +" y = yank = copy +" P paste before cursor +" p paste after cursor + + + +" Basic Vim navigation +" :sp file -- this will open a new file horizontally +" :vsp file -- will open a file splitting vertically +" ctrl-w w -- this will toggle to another open vim window From cfc9f92cb49ead60ef554fcc043354663cee48f6 Mon Sep 17 00:00:00 2001 From: jrtechs Date: Sun, 21 Apr 2019 16:52:28 -0400 Subject: [PATCH 14/59] Created script to format markdown paragraphs following a stringent column max. --- other/markdownParagraphFormatter.py | 121 ++++++++++++++++++++++++++++ 1 file changed, 121 insertions(+) create mode 100644 other/markdownParagraphFormatter.py diff --git a/other/markdownParagraphFormatter.py b/other/markdownParagraphFormatter.py new file mode 100644 index 0000000..1840d0b --- /dev/null +++ b/other/markdownParagraphFormatter.py @@ -0,0 +1,121 @@ +""" +Jeffery Russell +2019-4-21 + +Simple program to reformat paragraphs in markdown text files +to follow a specific col limit. +""" + +import os +import sys + + +def formatChunk(stringContent, charLimit): + """ + Formats a markdown section with with a specific + col limit. This only makes changes if the section is a + paragraph and nothing else. + + The only guarantee for the input is that there + are no lines which only contain a new line or space. + + :param stringContent: string of markdown chunk + :param charLimit: max character limit + :return: formatted string + """ + if len(stringContent.strip(" ")) == 0: + return "" + elif not stringContent[0].isalpha(): + return stringContent + result = "" + line = "" + stringContent = stringContent.replace("\n", " ") + words = stringContent.split(" ") + + for word in words: + if len(line) == 0 or len(line) + len(word) < charLimit: + if not len(line) == 0: + line = line + " " + line = line + word + else: + result = result + line + "\n" + line = word + if line != "": + result = result + line + "\n" + return result + + +def writeToFile(fileName, content): + """ + Writes to a file, overwriting the existing + output. + :param fileName: + :param content: + :return: + """ + f = open(fileName, "w+") + f.write(content) + f.close() + + +def wrapMarkdownParagraphsToColLimit(fileName, charLimit): + """ + Breaks apart a markdown file into chunks. A chunks are + separated by a blank lines. Each chunk is then + rendered according to our 80 char rules defined + in the formatChunk section. + :param fileName: + :param charLimit: + :return: + """ + result = "" + tempResult = "" + with open(fileName) as file: + for line in file: + if line.strip(" ") == "\n": + result = result + formatChunk(tempResult, charLimit) + tempResult = "" + result = result + "\n" + else: + tempResult = tempResult + line + print(line) + if tempResult != "": + result = result + formatChunk(tempResult, charLimit) + return result + + +def print_usage(): + """ + Prints script usage. + :return: + """ + print("Usage: file name -t (optional)") + print("\t-p simply prints the formatted output.") + print("\tfile name -- runs the command overwriting the existing file.") + + +def main(): + """ + Checks command line input and calls the proper formatting + functions. + :return: + """ + if len(sys.argv) > 1: + fileName = os.getcwd() + "/" + sys.argv[1] + if len(sys.argv) == 3 and sys.argv[2].lower() == "-p": + print(wrapMarkdownParagraphsToColLimit(fileName, 70)) + else: + writeToFile(fileName, + wrapMarkdownParagraphsToColLimit(fileName, 70)) + else: + print_usage() + + +""" +Makes sure that other scripts don't execute the main +""" +if __name__ == '__main__': + try: + main() + except KeyboardInterrupt: + panic() From fe145214b1679a6954bde4268b7a99e4c658656d Mon Sep 17 00:00:00 2001 From: jrtechs Date: Tue, 23 Apr 2019 21:51:37 -0400 Subject: [PATCH 15/59] Updated code to work with code blocks when there are new lines in it. --- other/markdownParagraphFormatter.py | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-) diff --git a/other/markdownParagraphFormatter.py b/other/markdownParagraphFormatter.py index 1840d0b..dca9fad 100644 --- a/other/markdownParagraphFormatter.py +++ b/other/markdownParagraphFormatter.py @@ -70,15 +70,23 @@ def wrapMarkdownParagraphsToColLimit(fileName, charLimit): """ result = "" tempResult = "" + inCodeBlock = False + with open(fileName) as file: for line in file: - if line.strip(" ") == "\n": + + if line.startswith("```"): + inCodeBlock = not inCodeBlock + result = result + line + elif inCodeBlock: + result = result + line + elif line.strip(" ") == "\n": result = result + formatChunk(tempResult, charLimit) tempResult = "" result = result + "\n" else: tempResult = tempResult + line - print(line) + if tempResult != "": result = result + formatChunk(tempResult, charLimit) return result From b92ba144f3c24534f472d7d8bbc3865d0c1cd801 Mon Sep 17 00:00:00 2001 From: jrtechs Date: Tue, 23 Apr 2019 22:04:25 -0400 Subject: [PATCH 16/59] Added comments to GA algo --- geneticAlgorithm/geneticAlgo.html | 150 ++++++++++++++++++++++++------ 1 file changed, 121 insertions(+), 29 deletions(-) diff --git a/geneticAlgorithm/geneticAlgo.html b/geneticAlgorithm/geneticAlgo.html index e8f31d9..c09a7a2 100644 --- a/geneticAlgorithm/geneticAlgo.html +++ b/geneticAlgorithm/geneticAlgo.html @@ -12,6 +12,12 @@