Post Bootcamp Graduation Advice
Tags: webdev, beginners
Published: 2023-01-03 18:46:27

A new year and the job search continues. Hopefully the new year will bring me into my new career. 

With that said, I have some exciting news. I just started a volunteer web developer position and my first stand up is tomorrow. I am really excited for this opportunity and excited to work on a professional team of other developers. 

Last year was hard on the tech industry and well, everyone. To any fellow graduates from last year, keep your head up and go easy on yourself. It has been hard for everyone to find a job, especially junior developers. I have definitely spiraled a lot this year with thinking I am not good enough, but forgetting that it was just a bad year to be switching into the field. If you also did the Flatiron Bootcamp, I highly suggest taking a supplementary algorithm and data structure class and doing lots of leetcode. I am currently taking Colt Steele's JavaScript Algorithm and Data Structures masterclass through Udemy and it has helped me so much. I do great in my interviews, but then the technical interview shows up and often I have been given a data structure I haven't used before. I was practicing for an interview for a company and saw a lot of the practice questions dealt with stacks and binary search trees, which I knew nothing about. I studied the masterclass as much as I could before the interview and felt more prepared than I ever had before. It was nice that this interview also had a real person that I could talk to and bounce ideas off of. It is great to talk things out with someone else so you don't get stuck and panic which is what tends to happen when I have been doing the unpaired interviews. Just remember to breathe and do the best you can. Always write out pseudocode first. Think about what are your inputs and outputs. What are your edge cases? Can you get around sorting and nested loops to save on your time and space complexity? If you are stuck on some aspect, code a simpler solution that maybe doesn't meet all parameters but at least gets you going in the right direction. 

I also wanted to provide some information on the different data structures I have learned about so far. I hope this little cheat sheet will help you in your engineering/developer journey. Wishing everyone a better year!

Stacks: 
- data collections
- abstract data structure
	- basically a set of rules for storing data in a certain way
- needs a last in first out (LIFO) data structure 
	- the last element added to the stack will be the first element removed from the stack
	- similar to the call stack
- Where are stacks used?
	- managing function invocations
	- undo/redo functionality 
		- think of how photoshop undos the last action 
		- routing (the history object) is treated like a stack
- array implementation
	- JS does not have a built in method for stacks 
	- use .push()  and .pop()  on an array makes a stack
	- can use .unshift()  and shift()
		- however this is more cost heavy because everything has to be re-indexed everytime 
		- also note that you can either use push and pop OR unshift and shift  
- linked list implementation
- Big O
	- insertion O(1)
	- deletion O(1)
	- access O(n)
	- searching O(n)  

Queues: 
- First in first out (FIFO) data structure
- adding and removing 
- array implementation 
	- var queue = []
	- can use push and  shift
		- heavy to use because of having to reindex
	- can use unshift and pop
		- also heavy with the reindex 
- linked list implementation  
	- lighter weight
- Big O
	- insertion O(1)
	- deletion O(1)
	- access O(n)
	- searching O(n)

Trees:
- Types
	- there are so many types however we focus on the following
	- tree
	- binary tree
		- each node can have at most two children 
	- binary search tree
		- special case of a binary tree
		- each node can have at most two children 
		- sorted in a particular way 
		- used to store data that is comparable/ sortable 
		- if you take any node on the tree,  every item that is less than that node is located to the left, and every item that is greater than is to the right 
		- great insertion and searching as it is sorted
		- the root is going to be a half way point so it makes it easier to compare and traverse 
		- compare and go to the left or the right, each time, you are cutting your options in half 

- Great for web scraping nested HTML
-  a step up from linked lists
- a data structure that consists of nodes in a parent/child relationship or a hierarchical structure
- type of a graph
- think of a branching tree but upside down
	- root - the top node from which everything branches from
	- child - a node directly connected to another node when moving away from the root
	- parent - the converse notion of a child
	- sibling - a group of nodes with the same parent
	- leaf - a node with no children/ the end of the line 
	- edge - the connection between one node and another
	- basically root connects to a parent which connects to a child, think of how state works in React
- nonlinear 
	- there can be many ways to reach a branching path 
	- a linked list is linear as there is only one direction you can go 
- not a tree
	- if there are nodes that reference each other on the same level  (sibling) aka they reference nodes that are not below them (children)
		- a node on a tree can only reference their children 
	- there can only be one root/ entry point
- USES
	- HTML DOM
		- the connection between each element 
		- think of how the body contains different div which have divs inside that, etc. 
	- network routing
	- abstract syntax trees
	- artificial intelligence 
	- folders in operating system
	- JSON

Heaps:
- Great for schedule/ priority task list
- a type of tree
- types: binary, fibonacci, pairing, leftist, etc. 
- Binary Heaps
	- two types: min and max heaps
		- MaxBinaryHeap
			- parent nodes are always larger than child nodes
			- what makes it different from a Binary Search Tree is that the children are smaller and the order of the children doesn't matter
			- root is always the largest
		- MinBinaryHeap
			- parent nodes are always smaller than child nodes
			- root is always the smallest
	- similar to a binary search tree, but with different rules
	- at most each parent can have two children 
	- compact as possible 
		- every left and right are filled out before moving up
	- used to implement priority queues and with graph traversal algorithms
	- can use an array to store a binary heap
	- for any index of an array (n) the left child is stored at 2n + 1 and the right child is at 2n + 2
	- for any child node at index n, its parent is at index Math.Floor((n -1) / 2)

Hash Tables: 
- aka hash map aka object (but with restrictions as objects typically deal with strings)
- built in to almost every programming language as a default type 
	- Python = dictionaries
	- JS = objects and maps
	- Java, Scala, and Go  = maps
	- Ruby = hashes
- used to store key-value pairs
- not ordered
- fast for all operations 
- hash function
	- implementing a hash table by using an array which you convert keys into valid array indices 
	- any function that can be used to map data of arbitrary size to data of a fixed size
		- so basically no matter what size the input is, it could be one or million characters, the output will always be the same size
		- however the output isn't something you can work backwards from, it is encrypted 
	- the values returned are called hash values, hash  codes, digests, or simply hashes
	- used in caches, crypto, authentication 
- What makes a good hash
	- O(1)
	- doesn't cluster outputs at specific indices, but distributes uniformly 
	- deterministic, every time you put in the same input you get the same output
- handle collision
	- when you have a hash function it is inevitable that you will have data that will be assigned the same index especially with small arrays like in the example
	- separate chaining 
		- you store pieces of data at the same spot/index in a more sophisticated data structure like a linked list or nested array
			- this allows you to store multiple key-value pairs at the same index
	- linear probing
		- you only store one piece of information at each index, if you have a collision/duplicate, then you search through the array and find the next empty spot
		- allows you to avoid nested data structures 
		- however you have to decide what you are going to do when you run out of room in your array
- Big O
	- insertion O(1)
	- deletion O(1)
	- access O(1)

Graphs:
- a data structure that consists of a finite (and possibly mutable) set of vertices or nodes or points, together with a set of unordered pairs of these vertices for an undirected graph or a set of ordered pairs for a directed graph 
- a collection of nodes and connections between those nodes 
- a tree is a type of graph
- no starting point or parent node
- models relationships
- uses
	- great for map/location data
	- user data
	- recommendation on social media
	- routing 
	- visual hierarchy
	- file system optimizations 
- Parts
	- vertex - a node
	- edge - connection between nodes
- types
	- directed graph
		- the edge has polarity or direction
		- directions assigned to distance between vertices
	- undirected graph
		- no direction between the edges
		- can traverse in any direction
	- weighted graph
		- values assigned to distances between vertices
		- the edge has a value
	- unweighted graph
		- no value to each edge
	- can be any combination of these
- Implementations
	- adjacency matrix
		- has vertices and edges 
		- 2D structure usually implemented with nested arrays with rows and columns 
		- takes up more space
		- slower to iterate over all edges
		- faster to lookup specific edge
		- for lots of data
	- adjacency list
		- use an array or list to store the edges 
		- or can store as hash table/object
		- can take up less space
		- faster to iterate over all edges
		- can be slower to lookup specific edge
		- most real world data tends to lend itself to adjacency lists as the data is sparse

Singly Linked Lists:
- an ordered list with fast inserts/removals at the beginning and end
	- as compared to arrays where shift and unshift are costly
	- although random access is not allowed
- a data structure that contains a head, tail, and length property
	- from the head you can figure out the next element 
	- think of it as a skyscraper without an elevator, you have to take the stairs and access each floor individually from the beginning
- consist of nodes
	- node is a piece of data or element
	- refers the next node
	- each node has a value and a pointer to another node || null
- a bunch of elements with no index pointing to the next element
- you have to start at the beginning to access elements
- excel at insertion and deletion and you don't need to access a random element 
- foundation to stacks and queues

Doubly Linked Lists:
- it is a singly linked list but adding a pointer to prev node and next node
- it is more flexible than a singly linked list, but it costs more memory
- no index, just pointers to the previous and next element