Successfully reported this slideshow.
We use your LinkedIn profile and activity data to personalize ads and to show you more relevant ads. You can change your ad preferences anytime.
Immutable collections
.NET
Under the hood
Dmitry Ivanov, JetBrains
Качество кода
1. Тесты всех видов, test coverage, property-based тесты
2. Preconditions for public methods, assertions for...
Чем мы займемся сегодня?
1. Поймём, где в вашем продукте иммутабельные
коллекции могут принести пользу и каким образом
2. ...
I. Мотивация
Mutable objects
class Point {
int X {get; set;}
int Y {get; set;}
Point(int x, int y) { X = x; Y = y; }
void IncreaseX(int...
Mutable objects
class Point {
int X {get; set;}
int Y {get; set;}
Point(int x, int y) { X = x; Y = y; }
void IncreaseX(int...
Shared state
class Point {
int X {get; set;}
int Y {get; set;}
Point(int x, int y) { … }
void IncreaseX(int xOffset) { … }...
Immutable
class Point { //could be struct
readonly int X;
readonly int Y;
Point(int x, int y) { X = x; Y = y; }
Point Incr...
Threading models
Message passingShared state
STA threads,
SynchronizationContext
BeginInvoke(), Invoke()
Single thread
UI Thread
Shared state
await
Use only one CPU core!
set 1
set 2
get != 2
012
Pessimistic locking
a1
a2
b1
Thread A Thread B
b2
lock
Readers-writer lock
a1
a2
b1
Thread A Thread B
b2
rwlock
Readers-writer lock
a1
a2
b1
Thread A Thread B
b2
rwlock
Thread C
c1
c2
Readers-writer lock
a1
a2
b1
Thread A Thread B
b2
rwlock
Thread C
c1
c2
Content model rwlock
start
calc
UI Thread Background threads
merge
Content model rwlock
start
calc
UI Thread Background threads
merge
write activity
Content model rwlock
start
calc
UI Thread Background threads
merge
write activity interrupts here
Should check Cancellatio...
Content model rwlock
start
calc
UI Thread Background threads
merge
write activity interrupts here
Should check Cancellatio...
Immutable model
State
Activity A Activity B
State A
State A’
State A’
State B
State B’
Immutable model
State
Activity A Activity B
State A
State A’
State A’
State B
State B’
Software transactional memory
Transaction 1 Transaction 2
read A
write B
Memory’
read B
write C
Memory
II. Иммутабельность
Immutable collections
System.Collections.Immutable
• Array
• Stack
• Queue
• List
• Dictionary (+ Sorted)
• Set (+Sorted)
...
Copy-on-write
class CopyOnWriteArray<T>
{
private readonly T[] _store;
private CopyOnWriteArray(T[] store) { _store = stor...
Copy-on-write
class ImmutableArray<T>
{
public static ImmutableArray<T> Empty =
new ImmutableArray(new T[0]);
private read...
Immutable stack
System.Collections.Immutable
• Array
• Stack
• Queue
• List
• Dictionary (+ Sorted)
• Set (+Sorted)
Algori...
Immutable stack
System.Collections.Immutable
Thread safe
Not linearizable
Immutable collections
System.Collections.Immutable
Thread safe
Not linearizable
Could be linearized by lock-free algorithm
Immutable to lock-free
SomeImmutableCollection collection = <initial>;
…
do {
int old = ds;
var new = transform(old);
} wh...
Lock-free stack
class LockFreeStack<T> {
ImmutableStack<T> immutable = <initial>;
void Push(T item) {
do {
var old = immut...
Immutable queue
System.Collections.Immutable
• Array
• Stack
• Queue
• List
• Dictionary (+ Sorted)
• Set (+Sorted)
Immutable queue
System.Collections.Immutable
• Array
• Stack
• Queue
• List
• Dictionary (+ Sorted)
• Set (+Sorted)
Immutable queue
System.Collections.Immutable
• Array
• Stack
• Queue
• List
• Dictionary (+ Sorted)
• Set (+Sorted)
Algori...
Immutable map & set
System.Collections.Immutable
• Array
• Stack
• Queue
• List
• Dictionary (+ Sorted)
• Set (+Sorted)
5
...
Immutable map & set
System.Collections.Immutable
• Array
• Stack
• Queue
• List
• Dictionary (+ Sorted)
• Set (+Sorted)
5
...
Immutable map & set
System.Collections.Immutable
• Array
• Stack
• Queue
• List
• Dictionary (+ Sorted)
• Set (+Sorted)
5
...
Immutable list
System.Collections.Immutable
• Array
• Stack
• Queue
• List
• Dictionary (+ Sorted)
• Set (+Sorted)
5
6
1 4...
Rope
8
gi
abc
def
6
9
var s = “abc” + “def” + “gi”
s.Insert(7, “h”)
ghi
Rope
8
gi
abc
def
6
9
var s = “abc” + “def” + “gi”
s.Insert(7, “h”)
3
g h
2 i
Rope
8
gi
abc
def
6
9
var s = “abc” + “def” + “gi”
s.Insert(7, “h”)
3
g h i
Rope
d,5
e,1
a,1 c,1
b,3
var s = “abcde”.Rope()
System.Collections.Immutable
• Array
• Stack
• Queue
• List
• Dictionary (...
More Ropes
var s = `some 1MB string`
16 refs|counts
16 refs|counts 16 refs|counts 16 refs|counts…
256 bytes block = 16*8*2...
III. Практика
Резюме
1. Теперь вы знаете почему выбор менее
производительной структуры данных может увеличить
производительность вашей к...
Что почитать?
• .NET Framework - Immutable Collections by Hadi Brais, March 2017
• Ropes: Theory and practice - IBM by Ami...
Вопросы и ответы
Вопрошающий
Любознательный
Посетитель
Лектор
blocking queue
(maxsize = 1)
Upcoming SlideShare
Loading in …5
×

.NET Fest 2018. Дмитрий Иванов. Иммутабельные структуры данных в .NET: зачем нужны и как устроены

24 views

Published on

Иммутабельные структуры данных - это производительность. Не производительность программы, а производительность программиста. Мы обсудим как иммутабельность помогает писать корректный многопоточный код быстрее. Рассмотрим другие смежные подходы, такие как readers-writer lock, actors и software transactional memory. Затем изучим широко распространенные структуры, такие как Rope, и попытаемся задизайнить многопоточное приложение на их основе. Под конец, мы погрузимся в System.Collections.Immutable и попытаемся понять, как реализовать иммутабельные коллекции эффективно.

Published in: Education
  • Be the first to comment

  • Be the first to like this

.NET Fest 2018. Дмитрий Иванов. Иммутабельные структуры данных в .NET: зачем нужны и как устроены

  1. 1. Immutable collections .NET Under the hood Dmitry Ivanov, JetBrains
  2. 2. Качество кода 1. Тесты всех видов, test coverage, property-based тесты 2. Preconditions for public methods, assertions for private 3. Compile-type checks: JetBrains Annotations ([NotNull], [Pure]), roslyn analyzers
  3. 3. Чем мы займемся сегодня? 1. Поймём, где в вашем продукте иммутабельные коллекции могут принести пользу и каким образом 2. Посмотрим на известные неизменяемые структуры 3. Изучим внутреннее устройство и потестируем производительность реализаций в .NET
  4. 4. I. Мотивация
  5. 5. Mutable objects class Point { int X {get; set;} int Y {get; set;} Point(int x, int y) { X = x; Y = y; } void IncreaseX(int xOffset) { X += xOffset; } void IncreaseY(int yOffset) { Y += xOffset; } }
  6. 6. Mutable objects class Point { int X {get; set;} int Y {get; set;} Point(int x, int y) { X = x; Y = y; } void IncreaseX(int xOffset) { X += xOffset; } void IncreaseY(int yOffset) { Y += xOffset; } }
  7. 7. Shared state class Point { int X {get; set;} int Y {get; set;} Point(int x, int y) { … } void IncreaseX(int xOffset) { … } void IncreaseY(int yOffset) { … } int GetHashCode() {…} bool Equals(object other) {…} } Point PolygonCircle Contexts Thread Pool
  8. 8. Immutable class Point { //could be struct readonly int X; readonly int Y; Point(int x, int y) { X = x; Y = y; } Point IncreaseX(int xOffset) => new Point(x + xOffset, y); Point IncreaseY(int yOffset) => new Point(x, y + yOffset); int GetHashCode() {…} bool Equals(object other) {…} }
  9. 9. Threading models Message passingShared state STA threads, SynchronizationContext BeginInvoke(), Invoke()
  10. 10. Single thread UI Thread Shared state await Use only one CPU core! set 1 set 2 get != 2 012
  11. 11. Pessimistic locking a1 a2 b1 Thread A Thread B b2 lock
  12. 12. Readers-writer lock a1 a2 b1 Thread A Thread B b2 rwlock
  13. 13. Readers-writer lock a1 a2 b1 Thread A Thread B b2 rwlock Thread C c1 c2
  14. 14. Readers-writer lock a1 a2 b1 Thread A Thread B b2 rwlock Thread C c1 c2
  15. 15. Content model rwlock start calc UI Thread Background threads merge
  16. 16. Content model rwlock start calc UI Thread Background threads merge write activity
  17. 17. Content model rwlock start calc UI Thread Background threads merge write activity interrupts here Should check CancellationToken
  18. 18. Content model rwlock start calc UI Thread Background threads merge write activity interrupts here Should check CancellationToken 1. Write unresponsiveness 2. Lots of checks 3. Lots of Assert(Read/Write) 4. Bad intermediate state
  19. 19. Immutable model State Activity A Activity B State A State A’ State A’ State B State B’
  20. 20. Immutable model State Activity A Activity B State A State A’ State A’ State B State B’
  21. 21. Software transactional memory Transaction 1 Transaction 2 read A write B Memory’ read B write C Memory
  22. 22. II. Иммутабельность
  23. 23. Immutable collections System.Collections.Immutable • Array • Stack • Queue • List • Dictionary (+ Sorted) • Set (+Sorted) • READ methods without changes: • Get, • Count, • GetEnumerator • … • WRITE methods returns collection type instead of void • Add • Insert • Remove • Clear • …
  24. 24. Copy-on-write class CopyOnWriteArray<T> { private readonly T[] _store; private CopyOnWriteArray(T[] store) { _store = store; } //read access doesn't copy public T Get(int index) => _store[index]; //write access always copy everything public CopyOnWriteArray<T> Set(int index, T item) { var newStore = new T[_store.Length]; _store.CopyTo(newStore, 0); //copy content newStore[index] = item; return new CopyOnWriteArray<T>(newStore); } }
  25. 25. Copy-on-write class ImmutableArray<T> { public static ImmutableArray<T> Empty = new ImmutableArray(new T[0]); private readonly T[] _store; private ImmutableArray(T[] store) { _store = store; } //read access doesn't copy public T Get(int index) => _store[index]; //write access always copy everything public ImmutableArray<T> Set(int index, T item) { … } public ImmutableArray<T> Add(T item) { … } public ImmutableArray<T> AddRange(T[] items) { … } }
  26. 26. Immutable stack System.Collections.Immutable • Array • Stack • Queue • List • Dictionary (+ Sorted) • Set (+Sorted) Algorithmic complexity is the same as mutable stack’s one
  27. 27. Immutable stack System.Collections.Immutable Thread safe Not linearizable
  28. 28. Immutable collections System.Collections.Immutable Thread safe Not linearizable Could be linearized by lock-free algorithm
  29. 29. Immutable to lock-free SomeImmutableCollection collection = <initial>; … do { int old = ds; var new = transform(old); } while (!CAS(ref collection, new, old)) //Compare-and-swap
  30. 30. Lock-free stack class LockFreeStack<T> { ImmutableStack<T> immutable = <initial>; void Push(T item) { do { var old = immutable; var new = old.Push(item); //new stack created! } while (Interlocked.CompareExchange(ref s, new, old) != old) } } ImmutableInterlocked.Push<T>(ref ImmutableStack<T> stack, T value)
  31. 31. Immutable queue System.Collections.Immutable • Array • Stack • Queue • List • Dictionary (+ Sorted) • Set (+Sorted)
  32. 32. Immutable queue System.Collections.Immutable • Array • Stack • Queue • List • Dictionary (+ Sorted) • Set (+Sorted)
  33. 33. Immutable queue System.Collections.Immutable • Array • Stack • Queue • List • Dictionary (+ Sorted) • Set (+Sorted) Algorithmic complexity is the same as mutable queue’s one
  34. 34. Immutable map & set System.Collections.Immutable • Array • Stack • Queue • List • Dictionary (+ Sorted) • Set (+Sorted) 5 6 1 4 7 8 2
  35. 35. Immutable map & set System.Collections.Immutable • Array • Stack • Queue • List • Dictionary (+ Sorted) • Set (+Sorted) 5 6 1 4 7 8 2 3
  36. 36. Immutable map & set System.Collections.Immutable • Array • Stack • Queue • List • Dictionary (+ Sorted) • Set (+Sorted) 5 6 1 4 7 8 2 5 2 4 3 Algorithmic for Get, Add, Remove: O(Log(N))
  37. 37. Immutable list System.Collections.Immutable • Array • Stack • Queue • List • Dictionary (+ Sorted) • Set (+Sorted) 5 6 1 4 7 8 2 5 2 4 3 Can’t be implemented like this because indexes shift right after insertion
  38. 38. Rope 8 gi abc def 6 9 var s = “abc” + “def” + “gi” s.Insert(7, “h”) ghi
  39. 39. Rope 8 gi abc def 6 9 var s = “abc” + “def” + “gi” s.Insert(7, “h”) 3 g h 2 i
  40. 40. Rope 8 gi abc def 6 9 var s = “abc” + “def” + “gi” s.Insert(7, “h”) 3 g h i
  41. 41. Rope d,5 e,1 a,1 c,1 b,3 var s = “abcde”.Rope() System.Collections.Immutable • Array • Stack • Queue • List • Dictionary (+ Sorted) • Set (+Sorted) Algorithmic for Add, Remove: O(Log(N)) (Faster than mutable List)
  42. 42. More Ropes var s = `some 1MB string` 16 refs|counts 16 refs|counts 16 refs|counts 16 refs|counts… 256 bytes block = 16*8*2 = 128 chars 4 levels = 128*16*16*16 = 512K chars16 refs|counts 128 chars 128 chars 128 chars
  43. 43. III. Практика
  44. 44. Резюме 1. Теперь вы знаете почему выбор менее производительной структуры данных может увеличить производительность вашей команды 2. Теперь вы легко выберете самую подходящую системную коллекцию и проверите её скорость 3. Теперь вы можете легко написать свою супер- оптимальную иммутабельную коллекцию. Но это не точно…
  45. 45. Что почитать? • .NET Framework - Immutable Collections by Hadi Brais, March 2017 • Ropes: Theory and practice - IBM by Amin Ahmad, February 2008 • STM: https://groups.csail.mit.edu/tds/papers/Shavit/ShavitTouitou-podc95.pdf
  46. 46. Вопросы и ответы Вопрошающий Любознательный Посетитель Лектор blocking queue (maxsize = 1)

×