.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure, and More
Chase Zhang
August 4, 2017
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Table of Contents
Immutable Data Structure
Introduction
Immutable Stack & Tree
Example: Git
Lock-free Data Structure
Introduction
Atomic and Immutable
Log-Structured Merge Tree
Introduction
Basic Ideas
Summary
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Introduction
▶ Python’s String, Tuple
▶ ImmutableJS
▶ Scala & Clojure
▶ Docker images
▶ Functional programming!
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Introduction
▶ Easily undo
▶ Eliminates side effect
▶ Suitable for concurrency
▶ Better comparation performance (React)
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Introduction
How to implement immutable data structure?
▶ A naive method is to make a copy every time. Like Python’s string
▶ It will be too costly in both time and space, can we do better?
▶ We want less memory cost
▶ We can afford a little worse in time cost, but not such costly as make a copy
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Immutable Stack & Tree
Let’s see two simple examples.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Immutable Stack & Tree
Question
How to implement immutable stack?
▶ Support push and remove on the top
▶ Every operation will return a history id
▶ At anytime, we can retrieve a snapshot of the stack with a specific history id
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Immutable Stack & Tree
nil
Head-0
Figure: Immutable Stack: Initial
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Immutable Stack & Tree
nil
Head-1 Head-0
Figure: Immutable Stack: Push
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Immutable Stack & Tree
nil
Head-2Head-1 Head-0
Figure: Immutable Stack: Pop
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Immutable Stack & Tree
nil
Head-2Head-1
Head-3
Head-0
Figure: Immutable Stack: Push Again
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Immutable Stack & Tree
▶ Keep the pointer of head after each operation
▶ With any one of them, we can easily restore the corresponding snapshot of the stack.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Immutable Stack & Tree
Question
How to implement immutable tree?
▶ We have a tree like hierarchy structure which we can insert, change or remove a node
▶ We’d like to implement undo operation upon this data structure, that is, after a
series of operations, we can revert the whole tree to some previous status easily
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Directory
File
Figure: An example of tree
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Change This
Figure: An example of tree
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Immutable Stack & Tree
▶ Instead of modifying a node in place, we’ll copy the path from it to the root and then
change the copied nodes.
▶ By doing this, the modified tree will share most nodes with the origin and thus will
save a lot of memory.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Example: Git
Let’s have a look at how Git makes use of these two algorithms
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Example: Git
Git’s internal objects are all located under .git/objects folder
.git
├── HEAD
├── objects
│   ├── 0c
│   ├── 0d
│   ├── info
│   └── pack
├── refs
│   ├── heads
│ └── tags
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Example: Git
Git’s objects are compressed with zlib, we can use the following program to decompress it
#!/usr/bin/env python
# -*- coding: utf-8 -*-
import sys
import zlib
def main(fname):
with open(fname) as f:
print zlib.decompress(f.read())
if __name__ == "__main__":
main(sys.argv[1])
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Example: Git
A better way is to use the build-in command
git cat-file -p 5b67fd90081
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Example: Git
DEMO TIME!
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Change This
Commit 0 Commit 0 Commit 1
Figure: Git Objects Model
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Immutable Data Structure
Example: Git
Conclusion
Git’s internal objects are just organized by the two simple immutable data structures
introduced before!
If the whole Git’s market worth 5 billion dollars, these two algorithms can just make up a
portion of 2.5 billion !
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Lock-free Data Structure
Yet, one more thing...
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Lock-free Data Structure
Introduction
Lock-free data structure are a wide range of data structures which allow safe concurrent
access without lock.
A single lock-free data structure may only worth only 10% of 2.5 billion, but its value will
double every 18 months.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Lock-free Data Structure
Atomic and Immutable
Lock-free is way too big a topic to discuss here, here we’ll only consider a small portion of it
which has some relationship with immutable data structures.
▶ We have atomic operation which is a faster alternative to lock for data safety in
concurrent environment
▶ Different processes can modify an immutable data structure in parallel and won’t
interfere each other
▶ Combining the two, we can implement mutable lock-free data structure easily.
Let’s take immutable tree as an example...
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Lock-free Data Structure
Atomic and Immutable
AtomicReference: root
Figure: Lock-free tree: initial
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Lock-free Data Structure
Atomic and Immutable
AtomicReference: root
XFigure: Lock-free tree: transit
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Lock-free Data Structure
Atomic and Immutable
AtomicReference: root
Will be recycled by GC
Figure: Lock-free tree: finish
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Lock-free Data Structure
Atomic and Immutable
As the reference is changed atomically, there is no need to lock the data structure when
accessing it in parallel.
What if two processes modified the same part simutaneously and thus caused a conflict?
We have while statement and CompareAndSet. At least one process will execute
successfully and eventually every process will finish their work.1
1
Yes, while statement may never exit in some cases for lock-free data structure. There exists a collection
of data structures which is said to be wait-free.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Lock-free Data Structure
Atomic and Immutable
The basic idea of lock-free data structure is that:
▶ we suppress the commitment of multiple consecutive operations into one single
operation that can be done atomically.
▶ This transaction of operations can only be regarded as success when the atomic
operation is done successfully, or all operations will fail and left no side effects.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Log-Structured Merge Tree
Let’s MAKE A BIG THING!
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Log-Structured Merge Tree
Introduction
▶ Immutable data structures make use of internal sharing memory to reduce time and
space cost
▶ Lock-free data structures make use of atomic operation to tackle concurrency
problem and achieve transactional like interface
▶ We’ll combine the two to get an awesome data structure: LSMT2
2
LSMT is much more complex than what we have talked here, but our discussion should be good enough
to give an impression of the basic idea
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Log-Structured Merge Tree
Introduction
Question
Design a storage solution for a big data warehouse:
1. Support basic database operations (CRUD) and variable field length
2. Support high performance parallell access with transactional-like interface. That
means, a series of operations can either success as a whole or fail as a whole. Never in
the middle
3. Extremely stable, even cut off electricity in the middle of writting disk can not
disturb the validity of data
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Log-Structured Merge Tree
Introduction
Why is it so hard?
▶ We have variable length fields, If we put rows adjacent to each other:
▶ how can we expand the space if user update one of them to a longer value?
▶ Once some values of a field has been deleted, there will be empty holes in the space,
how can we recycle them and reduce wasting.
▶ We want high performance for writing and reading, also the data should be persisted
successfully
▶ Concurrent access caused a huge complexity in implementation
▶ Data have to be written to sequential storage devices like hard disk, which is slow for
random access
▶ We want to be extremely stable, even a single write operation may not solid enough:
▶ Writing large log entry may be interrupted in the middle
▶ Undo and rollback a transaction can be interrupted in the middle
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Log-Structured Merge Tree
Basic Ideas
Log-Structured Merge Tree to rescue.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Log-Structured Merge Tree
Basic Ideas
▶ All data entries are organized as a tree (ex. B+ Tree)
▶ Draw ideas from immutable tree, every write operation can be transformed into
append operation by just writing new nodes to the end of file
▶ The root of the tree has been pointed by an on disk file upon which an update
operation can be regarded as atomical3
3
We can use append instead of overwrite so that even an append operation fails in the middle, we can
still recover former status
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Log-Structured Merge Tree
Basic Ideas
root
Append Only
Figure: Framework of LSMT
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Log-Structured Merge Tree
Basic Ideas
Figure: Only append copied nodes onto LSMT
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Log-Structured Merge Tree
Basic Ideas
root
Figure: File structure after appended new modification
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Log-Structured Merge Tree
Basic Ideas
root
X
Figure: Change the pointer of root to new place
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Log-Structured Merge Tree
Basic Ideas
root
Out of date
Figure: Root pointer has been changed atomically
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Log-Structured Merge Tree
Basic Ideas
Delete
Compress
Figure: Cleaning garbage blocks
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Log-Structured Merge Tree
Basic Ideas
The following projects are making use of LSMT:
▶ Bigtable (from Google)
▶ MongoDB
▶ SQLite 4
▶ Apache Cassandra
▶ InfluxDB
LSMT might be yet another example of billion worth algorithms.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Summary
Thank you!
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
.
Summary
One more word...
Algorithm skills is not for finding jobs.
It makes the difference between good and the best.

Immutable, and More