هل من الممكن مقارنة كتل اثنين من الهدف-C حسب المحتوى؟

StackOverflow https://stackoverflow.com/questions/2167932

سؤال

float pi = 3.14;
float (^piSquare)(void) = ^(void){ return pi * pi; };
float (^piSquare2)(void) = ^(void){ return pi * pi; };

[piSquare isEqualTo: piSquare2]; // -> want it to behave like -isEqualToString...
هل كانت مفيدة؟

المحلول

للتوسع في إجابة لوران.

الكتلة هي مزيج من التنفيذ والبيانات. لكي تكون كتلتين متساوية ، ستحتاج إلى الحصول على نفس التنفيذ بالضبط واستولت على نفس البيانات بالضبط. المقارنة ، وبالتالي ، تتطلب مقارنة كل من التنفيذ والبيانات.

قد يعتقد المرء أن مقارنة التنفيذ ستكون سهلة. في الواقع ليس بسبب الطريقة التي يعمل بها المحسن المترجم.

على الرغم من أن مقارنة البيانات البسيطة واضحة إلى حد ما ، فإن الكتل يمكن أن تلتقط الكائنات- بما في ذلك كائنات C ++ (والتي قد تعمل بالفعل في يوم من الأيام)- وقد تحتاج المقارنة أو لا تحتاج إلى أخذ ذلك في الاعتبار. التنفيذ الساذج من شأنه أن يقوم ببساطة بمقارنة مستوى البايت للمحتويات التي تم التقاطها. ومع ذلك ، قد يرغب المرء أيضًا في اختبار المساواة في الكائنات باستخدام مقارنات مستوى الكائن.

ثم هناك مسألة متغيرات __block. كتلة ، نفسها ، ليس لديها في الواقع أي بيانات بيانات تتعلق بالمتغيرات التي تم التقاطها __block لأنها لا تحتاجها لتلبية متطلبات المتغيرات المذكورة. وبالتالي ، لا يمكن للمقارنة مقارنة قيم __block دون تغيير كود المترجم بشكل كبير.

كل هذا يعني أنه ، لا ، من غير الممكن حاليًا مقارنة الكتل وتوضيح بعض الأسباب وراء ذلك. إذا شعرت أن هذا سيكون مفيدًا ، فقم بتقديم خطأ عبر http://bugreport.apple.com/ وتوفير حالة الاستخدام.

نصائح أخرى

وضع جانبا قضايا تنفيذ البرمجيات وتصميم اللغة ، ما تطلبه هو غير قابل للبراعة (ما لم تكن تهتم فقط بالكشف عن برامج متطابقة بنسبة 100 ٪). تحديد ما إذا كان برنامجان يحسبان نفس الوظيفة يعادل حل مشكلة التوقف. هذه نتيجة كلاسيكية لنظرية رايس: أي خاصية "مثيرة للاهتمام" لآلات تورينج أمر غير قابل للانسداد ، حيث "مثيرة للاهتمام" تعني أنه صحيح بالنسبة لبعض الآلات والخطأ للآخرين.

فقط للمتعة ، هذا هو الدليل. نفترض أننا يستطيع قم بإنشاء وظيفة لتحديد ما إذا كانت كتلتين مكافئة ، تسمى Eq (B1 ، B2). الآن سنستخدم هذه الوظيفة لحل مشكلة التوقف. نقوم بإنشاء وظيفة جديدة (M ، i) التي تخبرنا إذا كان Turing Machine M سيتوقف على المدخلات التي أحبها:

BOOL HALT(M,I) {
  return EQ(
    ^(int) {return 0;},
    ^(int) {M(I); return 0;}
  );
}

إذا توقفت M (i) ، فإن الكتل متكافئة ، لذلك توقف (M ، i) نعم. إذا لم تتوقف M (i) ، فستكون الكتل ليس ما يعادل ، لذلك توقف (م ، ط) لا. لاحظ أنه ليس علينا ذلك نفذ - اعدم الكتل - يمكن لوظيفة EQ الافتراضية لدينا حساب معادلةها فقط من خلال النظر إليها.

لقد حلنا الآن مشكلة التوقف ، والتي نعرف أنها غير ممكنة. لذلك ، لا يمكن أن يوجد EQ.

لا أعتقد أن هذا ممكن. يمكن اعتبار الكتل تقريبًا وظائف متقدمة (مع الوصول إلى المتغيرات العالمية أو المحلية). بنفس الطريقة التي لا يمكنك مقارنة محتوى الوظائف ، لا يمكنك مقارنة محتوى الكتل.

كل ما يمكنك فعله هو مقارنة التنفيذ منخفض المستوى, ، لكنني أشك في أن المترجم سيضمن أن كتلتين مع نفس المحتوى يشتركان في تنفيذها.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top