صفيف فورتران إلى C مجموعة. أرادت الحيل الكلي غبي

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

  •  03-07-2019
  •  | 
  •  

سؤال

ولدي هذا "مبسط" كود فورتران

real B(100, 200) 
real A(100,200)

... initialize B array code.

do I = 1, 100
  do J = 1, 200
    A(J,I) = B(J,I)
  end do
end do

واحدة من معلمو البرمجة حذر لي، وهذا فورتران يصل البيانات بشكل فعال في ترتيب الأعمدة، في حين ج يصل البيانات بشكل فعال في ترتيب الصفوف. وأشار إلى أن I نلقي نظرة فاحصة على الرمز، وتكون على استعداد لتبديل الحلقات حول الحفاظ على سرعة البرنامج القديم.

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

هل لديك أي اقتراحات؟

هل كانت مفيدة؟

المحلول

في C، المصفوفات متعددة الأبعاد تعمل مثل هذا:

#define array_length(a) (sizeof(a)/sizeof((a)[0]))
float a[100][200];
a[x][y] == ((float *)a)[array_length(a[0])*x + y];

وبعبارة أخرى، انهم صفائف مسطحة حقا و[][] هو السكر فقط النحوي.

وافترض القيام بذلك:

#define at(a, i, j) ((typeof(**(a)) *)a)[(i) + array_length((a)[0])*(j)]
float a[100][200];
float b[100][200];
for (i = 0; i < 100; i++)
    for (j = 0; j < 200; j++)
        at(a, j, i) = at(b, j, i);

وأنت تسير بشكل تسلسلي من خلال الذاكرة، والتظاهر وضعت أن a وb فعلا من أجل عمود كبير. انها نوع من الرهيبة في هذا a[x][y] != at(a, x, y) != a[y][x]، ولكن طالما أن نتذكر أن أنه غرر بها مثل هذا، سوف يكون على ما يرام.

تحرير

والرجل، وأشعر غبية. والقصد من هذا التعريف هو جعل at(a, x, y) == at[y][x]، ويفعل. حتى أبسط من ذلك بكثير وأسهل للفهم

#define at(a, i, j) (a)[j][i]

وسيكون من الأفضل أن ما ذكر أعلاه.

نصائح أخرى

هل أنت متأكد من الرجال FORTRAN بك لم الأمور في نصابها الصحيح؟

والمقتطف الذي نشر في الأصل يتم الوصول بالفعل صفائف في صف كبير النظام (الذي هو "غير فعالة" لFORTRAN، 'فعال' لC).

وكما يتضح من مقتطف الشفرة وكما ورد في سؤالك، والحصول على هذا 'صحيح' يمكن أن تكون عرضة للخطأ. قلق بشأن الحصول على رمز FORTRAN استدار إلى C لأول مرة دون الحاجة إلى القلق حول تفاصيل مثل هذا. عندما يعمل الميناء - ثم يمكنك تقلق حول تغيير العمود النظام يصل إلى صف النظام بالوصول (إذا كان يهم حقا حتى بعد يعمل الميناء)

وكان واحد من بلدي أول وظيفة البرمجة من الكلية لإصلاح التطبيق المستمر منذ فترة طويلة-C التي تم تصديرها من FORTRAN. وكانت صفائف أكبر بكثير من يدكم، وأنه تم أخذ شيء حوالي 27 ساعة في التشغيل. بعد تحديد ذلك، ركضوا في حوالي 2.5 ساعة ... حلوة جدا!

(OK، فإنه في الحقيقة لم يكن تعيين، لكنني كنت غريبة وجدت مشكلة كبيرة مع التعليمات البرمجية الخاصة بهم. لم بعض القدامى لا تريد مني بكثير على الرغم من هذا الإصلاح.)

ويبدو أن وجدت نفس المشكلة هنا.

real B(100, 200) 
real A(100,200)

... initialize B array code.

do I = 1, 100
  do J = 1, 200
    A(I,J) = B(I,J)
  end do
end do

وحلقات لديك (ليكون FORTRAN جيد) ستكون كما يلي:

real B(100, 200) 
real A(100,200)

... initialize B array code.

do J = 1, 200
  do I = 1, 100
    A(I,J) = B(I,J)
  end do
end do

وإلا فإنك نسير من خلال صفائف في الصف كبيرا، التي يمكن أن تكون فعالة للغاية.

وعلى الأقل أنا أعتقد أن هذا كيف يمكن ان تكون في FORTRAN - انها كانت فترة طويلة

.

ورأى لكم تحديث رمز ...

والآن، وكنت ترغب في مبادلة متغيرات التحكم حلقة بحيث يمكنك تكرار على الصفوف ومن ثم داخل هذا أعاد على الأعمدة إذا كنت تقوم بتحويل إلى C.

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