
لقد مرت ستة أشهر ، مما يعني أن الوقت قد حان لتثبيت جافا جديدة ! لقد كانت رحلة طويلة ، ووصل القليلون إلى النهاية. سقطت الخطوط الخام من JEPs مثيرة للاهتمام ، لكننا سنتحدث عن الباقي تحت الخفض.
كيف الحال؟
يتم إصدار الإصدار الجديد من Java وفقًا لدورة الإصدار "المتسارع" الجديدة التي يبلغ طولها حوالي ستة أشهر. يتم تحديد التواريخ المحددة في صفحة المشروع . كانت هناك عدة مراحل رئيسية لـ JDK 12:
- 2018/12/13 - المرحلة الأولى من التباطؤ (في هذه اللحظة ، شوكة مصنوعة من الفرع الرئيسي في المستودع) ؛
- 2019/01/17 - المرحلة الثانية من التباطؤ (أكمل كل ما هو ممكن) ؛
- 2019/02/07 - مرشح الإصدار (يتم إصلاح الأخطاء الأكثر أهمية فقط) ؛
- 2019/03/19 - الإصدار ، التوفر العام. <- أنت هنا
ماذا لدينا من هذا الجدول؟ نعم ، في الواقع ، لا شيء - لقد وصلنا للتو إلى خط النهاية ، ونشاهد عشاق الإرث من قمة JDK 12 الجديدة تمامًا.
البق! ذعر! كل ذلك إلى أسفل!

عندما يتم إصدار إصدار جديد بخلاف LTS ، عادةً ما لا يعجب الجميع بالميزات الجديدة. سيكون أكثر إثارة للاهتمام إذا كان كل شيء سوف ينهار إلى الجحيم.
بالطبع ، هناك أخطاء ، ولكن ليس في JDK 12 :) إذا حكمنا من خلال jir ، كل شيء طبيعي:

سوف أقتبس الطلب حتى تفهم تمامًا ما هي "القاعدة":
project = JDK AND issuetype = Bug AND status in (Open, "In Progress", New) AND priority in (P1) AND (fixVersion in (12) OR fixVersion is EMPTY AND affectedVersion in (12) AND affectedVersion not in regexVersion("11.*", "10.*", "9.*", "8.*", "7.*", "6.*")) AND (labels is EMPTY OR labels not in (jdk12-defer-request, noreg-demo, noreg-doc, noreg-self)) AND (component not in (docs, globalization, infrastructure) OR component = infrastructure AND subcomponent = build) AND reporter != "Shadow Bug" ORDER BY priority, component, subcomponent, assignee
بطبيعة الحال ، في الأخطاء العامة لديها مكان ليكون ، فإنها لن تذهب إلى أي مكان في مثل هذا المشروع الضخم. يُزعم أنه لم يتم ملاحظة حشرات P1 في الوقت الحالي.
تم الإعلان عن مزيد من الاتصالات الرسمية مع الأخطاء في وثيقة خاصة ، JEP 3: JDK Release Process ، والتي يملكها مضيفنا الخالد على موجات مضطربة من Java Ocean - Mark Reinhold.
وعلى وجه الخصوص ، يجدر حفر فقرة على من يقع اللوم وماذا يفعل؟ كيفية نقل التذاكر إذا لم يكن لديك وقت للإصدار الثاني عشر. من الضروري وضع علامة jdk$N-defer-request
في jdk$N-defer-request
والتي يشير فيها N إلى الإصدار الذي ترغب في نقله منه ، وترك تعليق ، السطر الأول منه هو Deferral Request . علاوة على ذلك ، تتم مراجعة جميع هذه الطلبات من قبل العملاء في المجالات والمشاريع المعنية.
لا يمكن تجاهل مشاكل اجتياز TCK بهذه الطريقة - من المضمون أن تظل Java جافا ، وليس شيئًا ما يشبه الضفدع. لا تختفي jdk$N-defer-request label
. من المثير للاهتمام ما يفعلونه مع الأشخاص الذين ينتهكون قاعدة عدم حذف العلامات - أقترح إطعام خنازير غينيا.
ومع ذلك ، يمكنك بهذه الطريقة معرفة عدد الأخطاء التي تم نقلها إلى JDK 13. دعنا نجرب هذا الاستعلام:
project = JDK AND issuetype = Bug AND status in (Open, "In Progress", New) AND (labels in (jdk12-defer-request) AND labels not in (noreg-demo, noreg-doc, noreg-self)) AND (component not in (docs, globalization, infrastructure) OR component = infrastructure AND subcomponent = build) AND reporter != "Shadow Bug" ORDER BY priority, component, subcomponent, assignee
قطعة واحدة فقط ، JDK-8216039 : "TLS with BC و RSASSA-PSS يكسر ECDHServerKeyExchange". انها ليست سميكة. إذا كانت هذه الحجة لا تزال غير مفيدة ، إذن ، كمحامٍ لك ، أوصي بتجربة مخدر.
وما هو بيت القصيد؟

من الواضح أن معظم الميزات لا تؤثر على المستخدمين (مبرمجو Java) ، ولكن مطوري OpenJDK نفسه. لذلك ، فقط في حالة ، أقسم الميزات إلى خارجية وداخلية . يمكنك تخطي تلك الداخلية ، لكنني أشعر بالإهانة ، لقد كتبت الكثير من النصوص.
189: شيناندواه: جامع للقمامة في وقت منخفض (تجريبي)
ميزة خارجية . باختصار ، الناس لا يحبون ذلك عندما يبطئ جافا ، خاصة إذا كانت اتفاقية مستوى الخدمة تتطلب استجابة من 10 إلى 500 مللي ثانية. الآن لدينا GC منخفضة منخفضة الحرة التي تحاول العمل أقرب إلى الحافة اليسرى من هذا النطاق. المفاضلة هي أننا نتبادل وحدة المعالجة المركزية وذاكرة الوصول العشوائي للحد من الكمون. تعمل مراحل وضع علامات الورك والضغط بالتوازي مع سلاسل عمليات التطبيق المباشرة. ترجع التوقفات الصغيرة المتبقية إلى حقيقة أنك ما زلت بحاجة إلى البحث عن جذور الرسم البياني للكائنات وتحديثها.
إذا لم يكن أي مما ذكر أعلاه منطقيًا بالنسبة لك - لا يهم ، فإن Shenandoah تعمل فقط ، بغض النظر عن فهم أو عدم فهم العمليات الأساسية.
يعمل أليكسي شيبيليف وكريستينا فلود ورومان كينك على ذلك - عليك أن تحاول جاهدة ألا تعرف عن هؤلاء الأشخاص. إذا كنت تفهم بشكل عام كيف تعمل GC ولكن لا تتخيل ما يمكن للمطور القيام به هناك ، أوصي بالنظر في الترجمة الرائعة لمقال Leshina الرائع "Homemade Garbage Collector for OpenJDK" أو JVM Anatomy Quarks series. هذا مثير جدا للاهتمام .
مهم للغاية. قررت أوراكل عدم شحن Sheandoah مع أي من إصداراتها - لا على jdk.java.net ولا على oracle.com. بالنظر إلى أن Shenandoah هي واحدة من أهم ميزات JDK 12 ، فإنه يستحق تثبيت بعض التجميع الرسمي الآخر ، على سبيل المثال ، من Azul .
230: جناح Microbenchmark
ميزة الداخلية . إذا حاولت أن تكتب العلامات الصغيرة ، فأنت تعلم أن ذلك يتم على JMH. JMH هو إطار عمل لإنشاء وتجميع وإطلاق وتحليل العلامات الصغيرة لجافا ولغات JVM الأخرى ، أنت نفسك تفهم من الذي كتبها (كل الصدف عشوائية). لسوء الحظ ، لا يمكن تطبيق كل ما يتم في عالم التطبيقات "العادية" داخل JDK. على سبيل المثال ، من غير المحتمل أن نرى رمز Spring Framework العادي على الإطلاق.
لحسن الحظ ، بدءًا من الإصدار 12 ، يمكنك استخدام JMH على الأقل ، وهناك بالفعل مجموعة من الاختبارات المكتوبة عليه. يمكنك أن ترى ذلك في jdk/jdk/test/micro/org/openjdk/bench
(يمكنك أن ترى مباشرة في المتصفح ، هذا المسار هو رابط).
على سبيل المثال ، إليك ما يبدو عليه اختبار GC .
واسمحوا لي أن أذكرك بأنه ليس لدينا StackOverflow هنا ، وأنه يحظر استخدام الشفرة من معجون النسخ ، هنا وفيما بعد ، دون قراءة ومراقبة جميع التراخيص من الملف المقابل ومشروع OpenJDK عمومًا ، وإلا فسوف تحصل بسهولة على آخر الجوارب في رفع دعوى.
@BenchmarkMode(Mode.AverageTime) @OutputTimeUnit(TimeUnit.NANOSECONDS) @State(Scope.Thread) public class Alloc { public static final int LENGTH = 400; public static final int ARR_LEN = 100; public int largeLen = 100; public int smalllen = 6; @Benchmark public void testLargeConstArray(Blackhole bh) throws Exception { int localArrlen = ARR_LEN; for (int i = 0; i < LENGTH; i++) { Object[] tmp = new Object[localArrlen]; bh.consume(tmp); } }
325: تبديل التعبيرات (معاينة)
ميزة خارجية . سيؤدي ذلك إلى تغيير نهجك في كتابة مفاتيح لا نهاية لها بطول أكثر من شاشتين. انظر:
فيرجن جافا سويتش ضد ...
int dayNum = -1; switch (day) { case MONDAY: case FRIDAY: case SUNDAY: dayNum = 6; break; case TUESDAY: dayNum = 7; break; case THURSDAY: case SATURDAY: dayNum = 8; break; case WEDNESDAY: dayNum = 9; break; }
لماذا يكون الأمر سيئًا : هناك الكثير من الرسائل ، يمكنك تخطي الاستراحة (خاصةً إذا كنت مدمنًا ، أو كنت مريضًا باضطراب فرط الحركة ونقص الانتباه).
... ضد تشاد جافا Swtich التعبير!
int dayNum = switch (day) { case MONDAY -> 0; case TUESDAY -> 1; default -> { int k = day.toString().length(); int result = f(k); break result; } };
لماذا جيدة : عدد قليل من الرسائل ، آمنة ومريحة ، ميزة باردة جديدة.
المكافأة : إذا كنت ساديًا ، فسوف يمنحك ذلك أقصى درجات الرضا ، حيث أن الآلاف من مطوري IDE يعانون الآن من عذاب بدعم هذه الميزة. نعم حكيم ، نعم؟ يمكنك إلقاء القبض عليه بعد التقرير يوم 6 أبريل واطلب بلطف أن يقدم كل التفاصيل القذرة.
هذه ميزة معاينة ، إنها لن تعمل! عند التجميع ، في javac
تحتاج إلى تمرير خيارات سطر الأوامر --enable-preview --release 12
، والتشغيل من خلال java
- فقط - --enable-preview
العلامة.
334: JVM Constants API
ميزة الداخلية . يريد المطورون التعامل مع ملفات الفئة. تحتاج إلى القيام بذلك بشكل ملائم ، وهذا هو بيان المشكلة. على الأقل ، هكذا قال برايان جويتز ، الذي يمتلك JEP :-) كل هذا جزء من ساحة معركة أكبر ، لكن في الوقت الحالي لن نتعمق.
تحتوي كل فئة من فئات Java على ما يسمى بـ "تجمع ثابت" حيث يوجد تفريغ لبعض القيم (مثل السلاسل والأحرف) أو كيانات وقت التشغيل مثل الفئات والطرق. يمكنك الحفر في هذا التفريغ باستخدام تعليمة ldc - "تحميل costant" ، لذلك كل هذا غير الهام يسمى الثوابت القابلة للتحميل. لا تزال هناك حالة خاصة ل invokeynamic ، ولكن لا يهم.
إذا عملنا مع ملفات classfiles ، فنحن نريد محاكاة أدوات bytecode بشكل ملائم ، وبالتالي - الثوابت القابلة للتحميل. الرغبة الأولى هي ببساطة إنشاء أنواع جافا المقابلة ، ولكن كيف تقدم لهم فئة "حية" ، بنية CONSTANT_Class_info
؟ تعتمد كائنات Class
على صحة وتناسق عملية تحميل الفصل ، ومع تحميل الفئات في Java ، يتم إنشاء bacchanalia الجهنمية. بادئ ذي بدء ، لا يمكن تحميل جميع الفئات في VM ، ولكن لا يزال يتعين عليك وصفها!
أرغب في إدارة أشياء مثل الفئات والطرق والوحوش الأقل شهرة ، مثل مقابض الطريقة والثوابت الديناميكية ، مع مراعاة كل هذه التفاصيل الدقيقة.
يتم حل هذه المشكلة عن طريق تقديم أنواع جديدة من القيم الرمزية للارتباطات الرمزية (بمعنى JVMS 5.1 ) ، يصف كل منها نوعًا محددًا من الثابت. يصف اسمياً بحتاً ، بمعزل عن فئات التحميل أو مشكلات الوصول. انهم يعيشون في حزم مثل java.lang.invoke.constant
ولا تسأل عن ذلك ، ولكن يمكنك إلقاء نظرة على التصحيح هنا .
340: منفذ AArch64 واحد ، وليس اثنين
ميزة خارجية . بالفعل في JDK 9 ، كان هناك موقف غريب عندما وضع Oracle و Red Hat منافذ ARM في نفس الوقت في حالة تأهب. وهنا نرى نهاية القصة: تمت إزالة الجزء 64 بت من ميناء Oraklov من المنبع.
كان بإمكانك الخوض في التاريخ لفترة طويلة بنفسك ، ولكن هناك طريقة أفضل. شاركت BellSoft في تطوير هذا JEP ، ويقع مكتبها في سان بطرسبرغ ، بجانب المكتب السابق لشركة أوراكل.
لذلك ، انتقلت على الفور إلى Alexey Voitilov ، CTO of BellSoft:
"BellSoft تطلق Liberica JDK ، التي ، بالإضافة إلى x86 Linux / Windows / Mac و Solaris / SPARC ، تدعم ARM. بدءًا من JDK 9 لـ ARM ، ركزنا على تحسين أداء منفذ AARCH64 لتطبيقات الخادم واستمرنا في دعم منفذ ARM 32 بت لـ لذلك ، في وقت إصدار JDK 11 ، كان هناك موقف حيث لا أحد يدعم جزء المنفذ 64 بت من Oracle (بما في ذلك Oracle) ، وقرر مجتمع OpenJDK إزالته من أجل التركيز على منفذ AARCH64. انظر، على سبيل المثال، JEP 315 ، وهو ما مدمجة في JDK 11) ، بدءًا من JDK 12 ، يدعم جميع الميزات الموجودة في المنفذ من Oracle (آخر ، Minimal VM ، قمت بدمجه في سبتمبر). لذلك ، كنت سعيدًا لمساعدة Bob Vandette على إزالة هذا الأساس في JDK 12. ونتيجة لذلك ، OpenJDK تلقى المجتمع منفذًا واحدًا على AARCH64 ومنفذ ARM32 واحدًا ، مما يسهل بالتأكيد دعمهم. "
341: افتراضي CDS المحفوظات
ميزة الداخلية . المشكلة هي أنه في بداية تطبيق Java ، يتم تحميل الآلاف من الفئات ، مما يخلق شعورًا بأن Java يتباطأ بدرجة كبيرة عند بدء التشغيل. لكن من هناك للكذب ، فهذا ليس مجرد "إحساس" - إنه كذلك. لإصلاح المشكلة من العصور القديمة ، تمارس الطقوس المختلفة.
تعد مشاركة بيانات الفصل هي ميزة جاءت إلينا منذ زمن بعيد ، مثل ميزة تجارية من JDK 8 Update 40. تتيح لك تجميع كل هذه البيانات المهملة عند بدء التشغيل في أرشيف يحتوي على بعض التنسيقات الخاصة بك (لا تحتاج إلى معرفة أي منها) ، وبعد ذلك سرعة الإطلاق التطبيقات في تزايد. وبعد فترة ، ظهر JEP 310 : مشاركة فئة بيانات التطبيق ، مما أتاح لنا التعامل بنفس الطريقة ليس فقط مع فئات النظام ، ولكن أيضًا مع فئات التطبيقات.
لفصول JDK ، يبدو هذا. أولاً ، نقوم بتفريغ الفئات باستخدام الأمر java -Xshare:dump
، ثم قم بتشغيل التطبيق ، java -Xshare:on -jar app.jar
منه استخدام ذاكرة التخزين المؤقت هذه: java -Xshare:on -jar app.jar
. كل شيء ، بدء التشغيل قد تحسنت قليلا. هل تعلم عن هذه الميزة؟ كثير من الذين لا يزالون لا يعرفون!
يبدو غريباً هنا: لماذا في كل مرة تكتب طقوساً - -Xshare:dump
إذا كانت النتيجة الافتراضية لهذا الأمر يمكن التنبؤ بها قليلاً حتى في مرحلة إنشاء توزيع JDK؟ وفقًا للوثائق ، إذا تم تثبيت توزيع Java 8 باستخدام برنامج التثبيت ، عندها يجب تشغيل الأوامر اللازمة لك فور تثبيته. مثل ، المثبت هو التعدين بهدوء في الزاوية. لكن لماذا؟ وماذا تفعل مع التوزيع ، والتي يتم توزيعها ليس بمثابة المثبت ، ولكن كملف مضغوط؟
الأمر بسيط: بدءًا من JDK 12 ، سيتم إنشاء أرشيف CDS بواسطة منشئي مجموعة التوزيع ، بعد الارتباط مباشرةً. حتى بالنسبة للبنيات الليلية (بشرط أن تكون 64 بت ووطنية ، وليس للتجميع المتقاطع).
لا يحتاج المستخدمون حتى إلى معرفة وجود هذه الميزة ، لأنه بدءًا من JDK 11 و -Xshare:auto
تمكين -Xshare:auto
بشكل افتراضي ، وسيتم انتقاء هذا الأرشيف تلقائيًا. وبالتالي ، مجرد حقيقة التحديث إلى JDK 12 تسرع إطلاق التطبيق!
344: المجموعات المختلطة المجهضة لـ G1
ميزة الداخلية . أن نكون صادقين أنا لا أفهم أي شيء في عمل G1 شرح لميزات GC مهمة ناكر للجميل. يتطلب فهم تفاصيل عمله من كل من الشرح والتفاهم. بالنسبة لمعظم الناس ، فإن GC هي نوع من الجحيم من صندوق السعوط الذي يمكنك خداعه في حالة حدوث شيء ما. لذلك ، يجب شرح المشكلة بطريقة أبسط.
المشكلة : G1 قد تعمل بشكل أفضل.
حسنًا ، المشكلة هي أن GC هي حل وسط للعديد من المعلمات ، واحدة منها هي طول التوقف. في بعض الأحيان يكون التوقف مؤقتًا طويلًا جدًا ، ومن الجيد أن تتمكن من إلغائه.
متى يحدث هذا؟ تحلل G1 فعليًا سلوك التطبيق وتختار واجهة العمل (يتم التعبير عنها كمجموعة مجموعة ) بناءً على استنتاجاتها. عندما تتم الموافقة على نطاق العمل ، تتعهد G1 بجمع جميع الكائنات الحية في مجموعة التجميع ، بعناد وبدون توقف ، في جلسة واحدة. في بعض الأحيان يستغرق الكثير من الوقت. في الجوهر ، هذا يعني أن G1 يحسب بشكل غير صحيح مقدار العمل. يمكنك خداعه عن طريق تغيير سلوك تطبيقك فجأة بحيث يعمل الدليل الإرشادي على إضافة بيانات سيئة عندما تدخل الكثير من المناطق القديمة في مجموعة التجميع.
من أجل الخروج من هذا الموقف ، تم الانتهاء من G1 من خلال الآلية التالية: إذا كان الكشف عن مجريات الأمور يختار بانتظام كمية العمل الخاطئة ، فانتقل G1 إلى جمع القمامة التزايدي ، خطوة بخطوة ، ويمكن إلغاء كل خطوة تالية (إذا لم تتناسب مع وقت التنفيذ المستهدف). ليس من المنطقي جمع شيء تدريجيًا (المناطق الناشئة) ، وبالتالي ، يتم تسليط الضوء على كل هذا العمل في الكتلة "الإلزامية" ، التي لا تزال تنفذ بشكل مستمر.
ماذا تفعل مع المستخدم النهائي؟ لا شيء ، تحتاج إلى الترقية إلى JDK 12 ، كل شيء سوف يتحسن بنفسه.
346: موجه إرجاع الذاكرة غير المستخدمة Committed من G1
ميزة الداخلية . المشكلة هي أنه إذا كان لدينا ورك كبير لا يستخدمه أي شخص بنشاط ، فيبدو من العدل استعادة كل هذه الذاكرة غير النشطة إلى نظام التشغيل. قبل JDK 12 ، ومع ذلك ، لم يحدث هذا.
من أجل تحقيق هدفها فيما يتعلق بطول الإيقاف المؤقت المسموح به ، تنفذ G1 مجموعة من الدورات الإضافية والمتوازية والمتعددة المراحل. في JDK 11 ، فإنه يعطي ذاكرة ملتزم بها لنظام التشغيل فقط مع GC الكامل ، أو أثناء مرحلة وضع العلامات الموازية. إذا قمت بتوصيل التسجيل (-Xloggc: /home/gc.log -XX: + PrintGCDetails -XX: + PrintGCDateStamps) ، فسيتم عرض هذه المرحلة بشيء من هذا القبيل:
8801.974: [G1Ergonomics (Concurrent Cycles) request concurrent cycle initiation, reason: occupancy higher than threshold, occupancy: 12582912000 bytes, allocation request: 0 bytes, threshold: 12562779330 bytes (45.00 %), source: end of GC] 8804.670: [G1Ergonomics (Concurrent Cycles) initiate concurrent cycle, reason: concurrent cycle initiation requested] 8805.612: [GC concurrent-mark-start] 8820.483: [GC concurrent-mark-end, 14.8711620 secs]
الطريف أن G1 ، بقدر ما تستطيع ، تكافح مع توقفات كاملة ، وتبدأ الدورة المتزامنة فقط مع تخصيصات متكررة وكومة مسدودة. وضعنا ، عندما لا يلمس أحد الورك ، هو عكس ذلك تماما. الحالات التي تحدث فيها خدوش G1 لإعطاء ذاكرة لنظام التشغيل ، نادرًا ما تحدث!
لذلك كان الجميع سيحرزون هذه المشكلة ("اشتروا المزيد من ذاكرة الوصول العشوائي ، التي تشبه المارقة!") ، إن لم يكن واحدًا - فهناك كل أنواع الغيوم والحاويات التي يعني هذا عدم كفاية استخدامها وفقدان أموال جدية. انظروا ، يا له من تقرير رائع ، مملوءة بالألم.
كان الحل هو تعليم G1 أن يتصرف بشكل جيد في هذه الحالة بالذات ، كما تعلم بالفعل Shenanda أو GenCon من OpenJ9. من الضروري تحديد الاستخدام غير الكافي للورك ، وبالتالي تقليل استخدامه. في بعض الاختبارات على Tomcat ، سمح ذلك بتقليل استهلاك الذاكرة بمقدار النصف تقريبًا.
خلاصة القول هي أن التطبيق يعتبر غير نشط ، أو إذا كان الفاصل الزمني (بالمللي ثانية) قد getloadavg()
منذ getloadavg()
الأخير ولم تكن هناك دورة متزامنة ، أو إذا getloadavg()
لفترة دقيقة واحدة حمولة أقل من عتبة معينة. بمجرد حدوث ذلك ، تبدأ عملية جمع البيانات المهملة بشكل دوري - بالتأكيد لن يتم تنظيفها وكذلك التجميع الكامل ، لكنها ستؤثر على التطبيق إلى الحد الأدنى.
يمكنك دفعها إلى هذا السجل:
(1) [6.084s][debug][gc,periodic ] Checking for periodic GC. [6.086s][info ][gc ] GC(13) Pause Young (Concurrent Start) (G1 Periodic Collection) 37M->36M(78M) 1.786ms (2) [9.087s][debug][gc,periodic ] Checking for periodic GC. [9.088s][info ][gc ] GC(15) Pause Young (Prepare Mixed) (G1 Periodic Collection) 9M->9M(32M) 0.722ms (3) [12.089s][debug][gc,periodic ] Checking for periodic GC. [12.091s][info ][gc ] GC(16) Pause Young (Mixed) (G1 Periodic Collection) 9M->5M(32M) 1.776ms (4) [15.092s][debug][gc,periodic ] Checking for periodic GC. [15.097s][info ][gc ] GC(17) Pause Young (Mixed) (G1 Periodic Collection) 5M->1M(32M) 4.142ms (5) [18.098s][debug][gc,periodic ] Checking for periodic GC. [18.100s][info ][gc ] GC(18) Pause Young (Concurrent Start) (G1 Periodic Collection) 1M->1M(32M) 1.685ms (6) [21.101s][debug][gc,periodic ] Checking for periodic GC. [21.102s][info ][gc ] GC(20) Pause Young (Concurrent Start) (G1 Periodic Collection) 1M->1M(32M) 0.868ms (7) [24.104s][debug][gc,periodic ] Checking for periodic GC. [24.104s][info ][gc ] GC(22) Pause Young (Concurrent Start) (G1 Periodic Collection) 1M->1M(32M) 0.778ms
احسب؟ انا لا. في JEP ، هناك ترجمة مفصلة لغة الإشارة لكل سطر من السجل ، وكيف تعمل الخوارزمية ، وكل شيء آخر.
"ماذا إذن ، لماذا اكتشفت ذلك؟" - أنت تسأل. الآن لدينا G1PeriodicGCInterval
: G1PeriodicGCInterval
و G1PeriodicGCSystemLoadThreshold
، والتي يمكن أن تكون ملتوية عندما تصبح سيئة. من المؤكد أنها ستكون سيئة يومًا ما ، إنها جافا ، حبيبي!
النتائج
نتيجة لذلك ، لدينا إصدار قوي بين أيدينا - ليس ثورة ، ولكن تطور يركز على تحسين الأداء. يرتبط نصف التحسينات تمامًا بالأداء: ثلاثة JEPs حول GC وواحدة حول CDS ، والتي تعد بأن تعمل من تلقاء نفسها ، تحتاج فقط إلى الترقية إلى JDK 12. بالإضافة إلى ذلك ، حصلنا على ميزة لغة واحدة (تعبيرات التبديل) ، أداتان جديدتان لمطوري JDK ( اختبارات Constants API و JMH) ، والآن يمكن للمجتمع التركيز بشكل أفضل على منفذ 64 بت واحد على ARM.
بشكل عام ، قم بالترقية إلى JDK 12 الآن ، وقد تكون القوة معك. سوف تحتاجها.
دقيقة من الإعلانات. قريبًا ، من 5 إلى 6 أبريل ، سيتم عقد مؤتمر JPoint ، والذي سيجمع عددًا كبيرًا من الأشخاص الذين يعرفون الكثير عن JDK وجميع أنواع الميزات الجديدة. على سبيل المثال ، سيكون هناك بالتأكيد سايمون ريتر من أزول مع محاضرة عن "JDK 12: مطبات لغير المعتاد" . المكان الأنسب لمناقشة أحدث إصدار! يمكنك معرفة المزيد حول JPoint على الموقع الرسمي .