Derleyici kodunuzu alır, çok basit talimatlara böler ve ardından bunları en uygun olduğunu düşündüğü şekilde yeniden birleştirir ve düzenler.
Kod
int i = 1;
int x = ++i + ++i;
aşağıdaki talimatlardan oluşur:
1. store 1 in i
2. read i as tmp1
3. add 1 to tmp1
4. store tmp1 in i
5. read i as tmp2
6. read i as tmp3
7. add 1 to tmp3
8. store tmp3 in i
9. read i as tmp4
10. add tmp2 and tmp4, as tmp5
11. store tmp5 in x
Ama benim yazdığım gibi numaralı bir liste olmasına rağmen, burada yalnızca birkaç sıralama bağımlılığı var: 1-> 2-> 3-> 4-> 5-> 10-> 11 ve 1-> 6-> 7- > 8-> 9-> 10-> 11 göreceli sıralarında kalmalıdır. Bunun dışında, derleyici özgürce yeniden sıralayabilir ve belki de fazlalığı ortadan kaldırabilir.
Örneğin, listeyi şu şekilde sipariş edebilirsiniz:
1. store 1 in i
2. read i as tmp1
6. read i as tmp3
3. add 1 to tmp1
7. add 1 to tmp3
4. store tmp1 in i
8. store tmp3 in i
5. read i as tmp2
9. read i as tmp4
10. add tmp2 and tmp4, as tmp5
11. store tmp5 in x
Derleyici bunu neden yapabilir? Çünkü artımın yan etkilerinin sıralaması yoktur. Ama şimdi derleyici basitleştirebilir: örneğin, 4'te ölü bir depo var: değerin üzerine hemen yazılır. Ayrıca, tmp2 ve tmp4 gerçekten aynı şeydir.
1. store 1 in i
2. read i as tmp1
6. read i as tmp3
3. add 1 to tmp1
7. add 1 to tmp3
8. store tmp3 in i
5. read i as tmp2
10. add tmp2 and tmp2, as tmp5
11. store tmp5 in x
Ve şimdi tmp1 ile yapılacak her şey ölü koddur: asla kullanılmaz. Ve i'nin yeniden okunması da ortadan kaldırılabilir:
1. store 1 in i
6. read i as tmp3
7. add 1 to tmp3
8. store tmp3 in i
10. add tmp3 and tmp3, as tmp5
11. store tmp5 in x
Bak, bu kod çok daha kısa. İyileştirici mutlu. Programcı değil, çünkü sadece bir kez artırıldım. Oops.
Bunun yerine derleyicinin yapabileceği başka bir şeye bakalım: orijinal sürüme geri dönelim.
1. store 1 in i
2. read i as tmp1
3. add 1 to tmp1
4. store tmp1 in i
5. read i as tmp2
6. read i as tmp3
7. add 1 to tmp3
8. store tmp3 in i
9. read i as tmp4
10. add tmp2 and tmp4, as tmp5
11. store tmp5 in x
Derleyici bunu şu şekilde yeniden sıralayabilir:
1. store 1 in i
2. read i as tmp1
3. add 1 to tmp1
4. store tmp1 in i
6. read i as tmp3
7. add 1 to tmp3
8. store tmp3 in i
5. read i as tmp2
9. read i as tmp4
10. add tmp2 and tmp4, as tmp5
11. store tmp5 in x
ve sonra iki kez okunduğumu tekrar fark edin, bu yüzden bunlardan birini kaldırın:
1. store 1 in i
2. read i as tmp1
3. add 1 to tmp1
4. store tmp1 in i
6. read i as tmp3
7. add 1 to tmp3
8. store tmp3 in i
5. read i as tmp2
10. add tmp2 and tmp2, as tmp5
11. store tmp5 in x
Bu güzel, ancak daha da ileri gidebilir: tmp1'i yeniden kullanabilir:
1. store 1 in i
2. read i as tmp1
3. add 1 to tmp1
4. store tmp1 in i
6. read i as tmp1
7. add 1 to tmp1
8. store tmp1 in i
5. read i as tmp2
10. add tmp2 and tmp2, as tmp5
11. store tmp5 in x
Daha sonra 6'da i'nin yeniden okunmasını ortadan kaldırabilir:
1. store 1 in i
2. read i as tmp1
3. add 1 to tmp1
4. store tmp1 in i
7. add 1 to tmp1
8. store tmp1 in i
5. read i as tmp2
10. add tmp2 and tmp2, as tmp5
11. store tmp5 in x
Şimdi 4 ölü bir depo:
1. store 1 in i
2. read i as tmp1
3. add 1 to tmp1
7. add 1 to tmp1
8. store tmp1 in i
5. read i as tmp2
10. add tmp2 and tmp2, as tmp5
11. store tmp5 in x
ve şimdi 3 ve 7 tek bir talimatta birleştirilebilir:
1. store 1 in i
2. read i as tmp1
3+7. add 2 to tmp1
8. store tmp1 in i
5. read i as tmp2
10. add tmp2 and tmp2, as tmp5
11. store tmp5 in x
Son geçici olanı ortadan kaldırın:
1. store 1 in i
2. read i as tmp1
3+7. add 2 to tmp1
8. store tmp1 in i
10. add tmp1 and tmp1, as tmp5
11. store tmp5 in x
Ve şimdi Visual C ++ 'nın size verdiği sonucu elde edersiniz.
Hiçbir şey yapmamak için talimatlar kaldırılmadığı sürece, her iki optimizasyon yolunda da önemli sipariş bağımlılıklarının korunduğunu unutmayın.