Bir meydan okuma için, bir kod golfçüsü aşağıdaki kodu yazdı :
import java.util.*;
public class Main {
public static void main(String[] args) {
int size = 3;
String[] array = new String[size];
Arrays.fill(array, "");
for(int i = 0; i <= 100; ) {
array[i++%size] += i + " ";
}
for(String element: array) {
System.out.println(element);
}
}
}
Bu kodu Java 8'de çalıştırdığınızda, aşağıdaki sonucu elde ederiz:
1 4 7 10 13 16 19 22 25 28 31 34 37 40 43 46 49 52 55 58 61 64 67 70 73 76 79 82 85 88 91 94 97 100
2 5 8 11 14 17 20 23 26 29 32 35 38 41 44 47 50 53 56 59 62 65 68 71 74 77 80 83 86 89 92 95 98 101
3 6 9 12 15 18 21 24 27 30 33 36 39 42 45 48 51 54 57 60 63 66 69 72 75 78 81 84 87 90 93 96 99
Bu kodu Java 10'da çalıştırdığınızda, aşağıdaki sonucu elde ederiz:
2 4 6 8 10 12 14 16 18 20 22 24 26 28 30 32 34 36 38 40 42 44 46 48 50 52 54 56 58 60 62 64 66 68 70 72 74 76 78 80 82 84 86 88 90 92 94 96 98
2 4 6 8 10 12 14 16 18 20 22 24 26 28 30 32 34 36 38 40 42 44 46 48 50 52 54 56 58 60 62 64 66 68 70 72 74 76 78 80 82 84 86 88 90 92 94 96 98 100 102
2 4 6 8 10 12 14 16 18 20 22 24 26 28 30 32 34 36 38 40 42 44 46 48 50 52 54 56 58 60 62 64 66 68 70 72 74 76 78 80 82 84 86 88 90 92 94 96 98 100
Numaralandırma tamamen Java 10 kullanılarak kapalı. Peki burada neler oluyor? Java 10'da bir hata mı?
Yorumlardan takip edin:
- Sorun, Java 9 veya üstü ile derlendiğinde ortaya çıkar (Java 10'da bulduk). Bu kodu Java 8'de derlemek, ardından Java 9'da veya Java 11 erken erişim de dahil olmak üzere daha sonraki bir sürümde çalıştırmak beklenen sonucu verir.
- Bu tür bir kod standart değildir, ancak spesifikasyonlara göre geçerlidir. Bu tarafından bulundu Kevin Cruijssen bir de bir tartışma golf meydan , karşılaşılan dolayısıyla tuhaf kullanım durumunda.
Didier L , sorunun çok daha küçük ve daha anlaşılır bir kodla yeniden üretilebileceğini öğrendi:
class Main { public static void main(String[] args) { String[] array = { "" }; array[test()] += "a"; } static int test() { System.out.println("evaluated"); return 0; } }
Java 8'de derlendiğinde sonuç:
evaluated
Java 9 ve 10'da derlendiğinde sonuç:
evaluated evaluated
Sorun dizisi birleştirme ve atama operatörü (sınırlı gibi görünüyor
+=
gibi, sol işlenen olarak yan etki (s) sahip bir ifade ile)array[test()]+="a"
,array[ix++]+="a"
,test()[index]+="a"
, veyatest().field+="a"
. Dize birleştirmeyi etkinleştirmek için kenarlardan en az birinin türü olmalıdırString
. Bunu başka türlerde veya yapılarda çoğaltmaya çalışmak başarısız oldu.
+=
Dolaylı String
referanslara uygulanması sınırlıdır . Bu yüzden önce diziniz bir olmalıdır String[]
. Sorun int[]
, long[]
ve arkadaşlarıyla oluşmuyor . Ama evet, temelde haklısın!
String[]
. Eğer öyleyse Object[]
ve yaparsanız array[expression] += "foo";
, aynıdır. Değil, yazın başvuruları tutmak gerekir Ama evet, bu, ilkel diziler için geçerli değildir String
( Object[]
, CharSequence[]
, Comparable[]
, ...), dize birleştirme sonucunu depolamak için.