Binary Trie Assignment

For this assignment, you are implementing an immutable Seq<E> using a binary trie. You are only writing a some of our normal Seq methods, the ones that work well with this data structure. That includes add, set, get, and iterator. You are not writing insert and remove as they are very non-optimal.

I have given you the structure of the code with an outer abstract class and two nested private inner classes that extend it. The inner classes represent an internal node and a leaf node. The leaf node is always nibble==0 so it doesn't store it. The internal nodes will be nibble > 0 depending on how high they are above the leaves. Remember that all leaves are at the same level.

Keep in mind that this is an immutable data structure. So add and set return new sequences without altering the originals.

I included two protected methods on the outer class. These are two methods that I found useful when writing my implementation. One tells you if a subtrie is full or not. If it is, nothing more can be added to it, so the addition does something at the level above it. The other gives you a new sibling for the current node with one element in it. This is useful in the situation where you found out that a subtrie was full.

I put a fair number of comments in the code to give pointers on things like the constructors that I created. I have several for both internal classes. Make sure you read the comments.

Test Code

Your test code needs to include tests of all the methods you have to implement.  You also need to make a sequence with at least 1000 elements in it to verify you can handle multiple levels.

Note that I added a tool to collect test coverage. If you are on a lab machine or you have gradle installed on your machine, you can run `gradle test`. This will generate a website in app/build/jacocoHtml/index.html. If you open this in your browser, and click on the csci2320 package, you can see your test coverage for TrieSet. I expect that to be at least 90%.