الصب بين المصفوفات متعددة الأبعاد وأحادية البعد

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

  •  09-06-2019
  •  | 
  •  

سؤال

جاء هذا من هذه الإجابة على سؤال سابق لي.هل هو مضمون للمترجم لعلاج array[4][4] كمثل array[16]?

على سبيل المثال، هل يقوم أي من المكالمات أدناه بـ api_func() تكون آمنة؟

void api_func(const double matrix[4][4]);

// ...

{
  typedef double Matrix[4][4];

  double* array1 = new double[16];
  double array2[16];

  // ...

  api_func(reinterpret_cast<Matrix&>(array1));
  api_func(reinterpret_cast<Matrix&>(array2));
}
هل كانت مفيدة؟

المحلول

من معيار C++، بالإشارة إلى sizeof المشغل أو العامل:

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

من هذا، أود أن أقول ذلك double[4][4] و double[16] يجب أن يكون لها نفس التمثيل الأساسي.

أي: معطى

sizeof(double[4]) = 4*sizeof(double)

و

sizeof(double[4][4]) = 4*sizeof(double[4])

إذن لدينا

sizeof(double[4][4]) = 4*4*sizeof(double) = 16*sizeof(double) = sizeof(double[16])

أعتقد أن المترجم المتوافق مع المعايير سيتعين عليه تنفيذ هذه الأمور بنفس الطريقة، وأعتقد أن هذا ليس شيئًا قد يكسره المترجم عن طريق الخطأ.تعمل الطريقة القياسية لتنفيذ المصفوفات متعددة الأبعاد كما هو متوقع.سيتطلب كسر المعيار عملاً إضافيًا، ومن دون أي فائدة على الأرجح.

ينص معيار C++ أيضًا على أن المصفوفة تتكون من عناصر مخصصة بشكل متجاور، مما يلغي إمكانية القيام بأي شيء غريب باستخدام المؤشرات والحشو.

نصائح أخرى

لا أعتقد أن هناك مشكلة في الحشو الذي تم تقديمه من خلال وجود ملف متعدد الأبعاد مجموعة مصفوفة.

يجب أن يفي كل عنصر في المصفوفة بمتطلبات الحشو التي تفرضها البنية.سيكون للمصفوفة [N] [M] دائمًا نفس تمثيل الذاكرة كواحدة من [M*N].

يجب أن يتم وضع كل عنصر من عناصر المصفوفة بشكل تسلسلي في الذاكرة بواسطة المترجم.الإعلانان بينما الأنواع المختلفة هي نفس بنية الذاكرة الأساسية.

@ كونراد رودولف:

لقد قمت بخلط هذين الاثنين (الصف الرئيسي/العمود الرئيسي) بنفسي، لكنني أعرف هذا:انها محددة جيدا.

int x[3][5]، على سبيل المثال، عبارة عن مصفوفة بالحجم 3، وعناصرها عبارة عن مصفوفات int بالحجم 5.(§6.5.2.1) إضافة جميع القواعد من المعيار حول المصفوفات والعنونة وما إلى ذلك.تحصل على أن الحرف الثاني يشير إلى أعداد صحيحة متتالية، في حين أن الحرف الأول سيشير إلى كائنات 5-int متتالية.(لذا فإن 3 هو الرقم الأكبر؛لديك 5 ints بين س[1][0] و س[2][0].)

سأكون قلقًا بشأن إضافة حشوة لأشياء مثل Matrix[5][5] لجعل كل كلمة في الصف متسقة، لكن هذا قد يكون مجرد خرافة خاصة بي.

السؤال الأكبر هو:هل أنت حقا بحاجة لأداء مثل هذا المدلى بها؟

على الرغم من أنك قد تكون قادرًا على الإفلات من العقاب، فسيظل من الأسهل قراءته وصيانته لتجنبه تمامًا.على سبيل المثال، يمكنك دائمًا استخدام double[m*n] كنوع فعلي، ثم العمل مع فئة تغلف هذا النوع، وربما تقوم بتحميل عامل التشغيل [] بشكل زائد لسهولة الاستخدام.في هذه الحالة، قد تحتاج أيضًا إلى فئة متوسطة لتغليف صف واحد - بحيث يظل رمز مثل my_matrix[3][5] يعمل كما هو متوقع.

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