diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 0000000..d0329df --- /dev/null +++ b/Dockerfile @@ -0,0 +1,13 @@ +FROM node:latest + +# Set working directoy +WORKDIR /usr/src/app + +# Copy dependencies and install +RUN npm install -g sibilant + +# Copy code +COPY crossbeam.lisp . + +CMD sibilant -x -f crossbeam.lisp + diff --git a/Makefile b/Makefile new file mode 100644 index 0000000..d672651 --- /dev/null +++ b/Makefile @@ -0,0 +1,7 @@ +test: package.json crossbeam.lisp + docker build . -t paul/crossbeam + docker run -it paul/crossbeam + +clean: + docker ps -a -q --filter ancestor=paul/crossbeam | xargs docker rm -f + docker image rm paul/crossbeam:latest diff --git a/README.md b/README.md index 277877b..680e627 100644 --- a/README.md +++ b/README.md @@ -1,3 +1,19 @@ -# crossbeam-assignment +# Assignment for Crossbeam -Tmp \ No newline at end of file +## The Challenge +You are given a list of tasks, some of which depend on others. Write a function which will takes a subset of those tasks and returns an ordered list of all the tasks to run. + +## My Algorithm +My algorithm appends dependancies using a recursive function + +This treats the dependancies like a tree. By treating these like a tree, the recursive algorithm traverses down the tree, then comes back up, appending each node along the way + +## Testing +Tests several sets of tasks by looking at a ", " seperated string from the array +Uses the string "undefined" to determine an error occured + +# To Run +Running `make` will spin up a docker instance and run crossbeam.lisp using sibilant + +## Clean Up +Run `make clean` to delete all contianers and images created by the run diff --git a/crossbeam.lisp b/crossbeam.lisp new file mode 100644 index 0000000..b7f77d4 --- /dev/null +++ b/crossbeam.lisp @@ -0,0 +1,103 @@ + +;; The challenge: You are given a list of tasks, some of which depend on +;; others. Write a function which will takes a subset of those tasks and +;; returns an ordered list of all the tasks to run. + + +;; My algorithm for append dependancies uses a recursive function +;; This treats the dependancies like a tree +;; The recursive algorithm traverses down the tree, then comes back up +;; appending along the way + + +;; Recursive function to add each task to the list +;; Use caution as recursive functions can overwhelm the stack +;; Recursion is used here as it simplifies appending new values +(def add-next (defined-depends, ordered-tasks, chosen-task) + (var is-valid-task false) + ;; Grab the task we are attempting to add and check it's dependancies + (each (each-defined-depends) defined-depends + (if (= each-defined-depends.task chosen-task) (do + (assign is-valid-task true) + (each (each-depends-depend) each-defined-depends.depends + ;; If the dependancy has not been added + ;; Add it using add-next, this keeps things in order + (unless (includes? ordered-tasks each-depends-depend) + (assign ordered-tasks + (add-next defined-depends ordered-tasks each-depends-depend) + ) + ) + ) + )) + ) + + ;; If we are given a valid task include it if it's not already there + ;; If it's a bad task append "undefined" to be checked later + (if is-valid-task + (if (not (includes? ordered-tasks chosen-task)) + (assign ordered-tasks (append ordered-tasks chosen-task)) + ) + (assign ordered-tasks (append ordered-tasks "undefined")) + ) + ordered-tasks +) + +;; Determines all tasks needed in what order +(def determine-order (defined-depends, chosen-tasks) + ;; Loop through each of the chosen tasks to add them to the list + ;; Use add-next recursive function + (var sorted []) + (each (each-chosen-task) chosen-tasks + (assign sorted (add-next defined-depends sorted each-chosen-task)) + ) + + ;; If any part of the returned result is undefined we were given bad tasking + (if (includes? sorted "undefined") + (assign sorted ["undefined"]) + ) + + sorted +) + +;; Run the tests and verify the results +;; expected-result is ", " sperated string representing the array +(def run-test (test-num example-defined-depends chosen-tasks expected-result) + (assign test-var (join (determine-order example-defined-depends chosen-tasks) ", ")) + ;;(assign test-var (determine-order example-defined-depends chosen-tasks)) + (if (= test-var expected-result) + (console.log ("-- success -- Test " test-num " -- " test-var)) + (console.log ("-- failure -- Test " test-num " -- " test-var)) + ) +) + +;; Test set sandwich +(var example-tasks + [ + {task "make a sandwich", depends ["buy groceries"]} + {task "buy groceries", depends ["go to the store"]} + {task "go to the store", depends []} + ] +) + +(run-test 1 example-tasks ["make a sandwich"] "go to the store, buy groceries, make a sandwich") +(run-test 2 example-tasks ["buy groceries" "make a sandwich"] "go to the store, buy groceries, make a sandwich") +(run-test 3 example-tasks ["buy groceries"] "go to the store, buy groceries") +(run-test 4 example-tasks ["make a sandwich" "buy groceries"] "go to the store, buy groceries, make a sandwich") +(run-test 5 example-tasks ["make sandwich" "buy groceries"] "undefined") + +;; Test set wrap +(var example-tasks + [ + {task "make a wrap", depends ["buy hummus", "buy wrap", "buy veggies"]} + {task "buy hummus", depends ["go to the store"]} + {task "buy wrap", depends ["go to the store"]} + {task "buy veggies", depends ["go to the store"]} + {task "go to the store", depends []} + ] +) + +(run-test 6 example-tasks ["make a wrap"] "go to the store, buy hummus, buy wrap, buy veggies, make a wrap") +(run-test 7 example-tasks ["go to the store" "make a wrap"] "go to the store, buy hummus, buy wrap, buy veggies, make a wrap") +(run-test 8 example-tasks ["buy wrap" "go to the store" "make a wrap"] "go to the store, buy wrap, buy hummus, buy veggies, make a wrap") +(run-test 9 example-tasks ["go to the store" "make a sandwich"] "undefined") + diff --git a/package.json b/package.json new file mode 100644 index 0000000..276be57 --- /dev/null +++ b/package.json @@ -0,0 +1,9 @@ +{ + "name": "crossbeam sibilent test", + "version": "1.0", + "description": "crossbeam assessment, sibilent task ordering", + "author": "Paul Halvorsen ", + "dependencies": { + "sibilant": "" + } +}