الغرض من نمط Singleton هو التأكد من أن الفصل لديه مثيل واحد فقط ويوفر أيضًا نقطة وصول عالمية لذلك. لمنع العمال الآخرين من إنشاء فصلنا ،
يمكنك إنشاء مُنشئ فريد لهذه الفئة وتعيين مرئي المنشئ إلى القطاع الخاص. تجدر الإشارة إلى أننا إذا أنشأنا مُنشئين آخرين غير خاصين ، أو لم نذكر أي فصل على الإطلاق
بالنسبة للمشاركين ، لا يزال بإمكان الآخرين إنشاء إنشاء فصلنا. إذا كنا لا نريد إنشاء كائن Singleton مقدمًا ، فيمكننا الانتظار حتى المرة الأولى التي نستخدم فيها كائن Singleton ، أي ،
تهيئة التأخر. هناك سببان للتخلف عن تهيئة الأشياء المفردة:
1. ربما في وقت التهيئة الثابتة ، ليس لديك معلومات كافية حول كيفية تهيئة كائن Singleton.
2. قد يكون الغرض من اختيار تهيئة التهيئة المتأخرة هو انتظار موارد مثل اتصالات قاعدة البيانات ، وخاصة في التطبيقات التي لا تكون هذه المفردة مطلوبة في جلسات معينة محددة.
إذا تمت تهيئة Singleton في بيئة متعددة مؤشرات الترابط ، فيجب أن نكون حريصين على منع خيوط متعددة من التهيئة في نفس الوقت.
عادةً ما يتم تصميم نمط Singleton بلغة Java:
Lazy Way: يشير إلى مثيل Singleton العالمي الذي يتم بناؤه عند استخدامه لأول مرة. تأخير تهيئة.
طريقة الجياع الرجل: يشير إلى مثيل واحد عالمي يتم بناؤه أثناء تحميل الفصل. تهيئة عاجلة.
1. سينغليتون الصيني الجائع
الطبقة العامة Singleton1 {private Singleton1 () {} // تحديد مثيلك الداخلي. // لاحظ أن هذا خاص. مثيل Singleton1 الخاص = New Singleton1 () ؛ /** * // ** * فيما يلي طريقة ثابتة للوصول الخارجي إلى هذه الفئة ، والتي يمكن الوصول إليها مباشرة * return */public static singleton1 getInstance () {return مثيل ؛ }}2. فئة Singleton Lazy
الطبقة العامة Singleton2 {مثيل خاص ثابت Singleton2 = null ؛ /*** // *** تم تحسين هذه الطريقة مقارنة بما سبق. لا يتطلب إنشاء كائنات في كل مرة ، ولكن في المرة الأولى * يولد مثيلات عند استخدامها ، مما يحسن الكفاءة! * @return */ public static singleton2 getInstance () {if (مثيل == null) مثيل = جديد singleton2 () ؛ مثيل العودة ؛ }}فيما يلي المشكلات الرئيسية متعددة الخيوط. في Singletons Lazy ، لا توجد مشكلة في خيوط واحدة ، ولكن عندما يكون هناك متعددة الخيوط ، قد يكون هناك حالتان أو أكثر من حالات Singletion2.
على سبيل المثال: عندما يكون موضوع الخيط 1 هذا مثيل == فارغًا صحيحًا ، عند مسح العملية الجديدة ، قبل إجراء العملية الجديدة وبعد إجراء العملية الجديدة ، يقوم مؤشر الترابط 2 فقط بإجراء عملية الحكم ، وما زال المثيل خيرًا. لذلك ، سيقوم الموضوع 2 أيضًا بإجراء العملية الجديدة. وهلم جرا ، تحت التزامن العالي ، قد يكون هناك حالتان أو أكثر من singletion2. من الواضح أن هذا غير صحيح.
لذلك ، قم بتغيير الرمز على النحو التالي:
الطبقة العامة Singleton3 {مثيل خاص ثابت Singleton3 = null ؛ /*** // *** تم تحسين هذه الطريقة مقارنة بما سبق. لا يتطلب إنشاء الكائن في كل مرة ، ولكن في المرة الأولى * ينشئ مثيلات عند استخدامها ، مما يحسن الكفاءة! * من أجل تجنب الأخطاء في الخيوط المتعددة ، تمت إضافة علامة المزامنة * @RETURN */ public static Synchronized Singleton3 getInstance () {if (مثيل == null) مثيل = جديد singleton3 () ؛ مثيل العودة ؛ }}لكن هذا يخلق مشكلة أخرى. تتم مزامنة الطرق في كل مرة يتم فيها استرداد المثيل. من الواضح أن الأداء يتأثر للغاية ، لذا استمر في تغيير الكود على النحو التالي:
متقلبة ، استبدل التزامن بتكلفة أقل
لماذا هو أرخص من التزامن؟
يتم تحديد تكلفة التزامن بشكل أساسي من خلال نطاق التغطية. إذا كان يمكن تقليل نطاق تغطية التزامن ، فيمكن تحسين أداء البرنامج بشكل كبير.
تغطية التقلب هي فقط على المستوى المتغير. لذلك ، فإن تكلفة التزامن منخفضة للغاية.
ما هو مبدأ التقلب؟
إن دلالات التقلب هي في الواقع إخبار المعالج بعدم وضعي في ذاكرة العمل ، يرجى تشغيلني مباشرة في الذاكرة الرئيسية. (انظر نموذج ذاكرة Java للذاكرة العاملة للحصول على التفاصيل)
لذلك ، عند الوصول إلى المتغير متعدد النواة أو متعدد الخيوط ، فإنها ستقوم بتشغيل الذاكرة الرئيسية مباشرة ، والتي تحقق مشاركة متغيرة بشكل أساسي.
ما هي مزايا التقلب؟
1. إنتاجية أكبر برنامج
2. كود أقل لتنفيذ متعدد الخيوط
3. البرنامج لديه قابلية التوسع أفضل
4. من الأسهل فهمها ، وليس هناك حاجة لتكاليف التعلم المرتفعة للغاية.
ما هي عيوب المتقلبة؟
1. عرضة للمشاكل
2. من الصعب التصميم
يتطلب الاستخدامات المتقلبة JDK الإصدار 1.5 وما فوق.
الرمز المحسن كما يلي (يسمى أيضًا قفل مزدوج):
الطبقة العامة Singleton4 {مثيل خاص ثابت Singleton4 ؛ /*** // *** قفل مزدوج لتحقيق تطبيق متعدد الخيوط وتحسين الأداء* @RETURN*/public static singleton4 getInstance () {if (مثيل == null) {synchronized (singleton4 // 3}} مثيل الإرجاع ؛ }}