[Arrays] ما هو تمثيل Haskell الموصى به لصفيفي البكسل ثنائية البعد بدون وفاق مع ملايين البكسل؟


Answers

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

على أي أساس يجب أن أختار بين Vector.Unboxed و UArray؟ وهي عبارة عن صفيفات غير محمولين ، ولكن يبدو أن التجريد المتجه إلى المعلمات يتم الإعلان عنه بشكل كبير ، خاصة حول اندماج الحلقات. هل المتجه دائما أفضل؟ إذا لم يكن الأمر كذلك ، فمتى يجب علي استخدام أي تمثيل؟

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

لا يمكن استخدام Vector.Unboxed مع الاستراتيجيات المتوازية. أظن أنه لا يمكن استخدام UArray ، ولكن على الأقل من السهل التبديل من UArray إلى Array المربوط ومعرفة ما إذا كانت الفوائد المتوازية تزيد من تكاليف الملاكمة.

بالنسبة للصور الملونة ، سوف أرغب بتخزين ثلاثة أضعاف من الأعداد الصحيحة من 16 بتة أو ثلاثية الأعداد ذات الفاصلة العائمة أحادية الدقة. لهذا الغرض ، هل يمكن استخدام Vector أو UArray بسهولة؟ المزيد من الأداء؟

حاولت استخدام المصفوفات لتمثيل الصور (على الرغم من أنني أحتاج إلى صور بتدرج الرمادي فقط). بالنسبة للصور الملونة ، استخدمت مكتبة Codec-Image-DevIL لقراءة / كتابة الصور (الارتباطات إلى مكتبة Devil) ، للصور ذات التدرج الرمادي ، استخدمت مكتبة pgm (نقية Haskell).

كانت مشكلتي الرئيسية مع Array أنها لا توفر سوى تخزين الوصول العشوائي ، ولكنها لا توفر العديد من الوسائل لبناء خوارزميات Array ولا تأتي مع مكتبات جاهزة للاستخدام من روتينات الصفيف (لا تتفاعل مع الجبر الخطي libs ، لا 'ر تسمح للتعبير عن التوليفات ، و fft والتحولات الأخرى).

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

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

لذلك فإن المشكلة مع المصفوفات هي أنها غير مناسبة بشكل جيد للحسابات الرقمية. Hmatrix 'Data.Packed.Vector و Data.Packed.Matrix أفضل في هذا الصدد ، لأنها تأتي جنبا إلى جنب مع مكتبة مصفوفة صلبة (الاهتمام: رخصة GPL). من حيث الأداء ، على تكاثر المصفوفة ، كانت hmatrix سريعة بما فيه الكفاية ( أبطأ قليلاً من Octave ) ، ولكنها متعطشة جداً للذاكرة (تستهلك عدة مرات أكثر من Python / SciPy).

توجد أيضًا مكتبة blas للمصفوفات ، ولكنها لا تعتمد على GHC7.

لم يكن لدي الكثير من الخبرة مع Repa بعد ، وأنا لا أفهم رمز repa جيدا. مما أراه من مجموعة محدودة جدًا من خوارزميات مصفوفة جاهزة للاستخدام ومكتوب عليها ، لكن على الأقل يمكن التعبير عن خوارزميات مهمة عن طريق وسائل المكتبة. على سبيل المثال ، هناك بالفعل إجراءات لمضاعفة المصفوفة وللفقية في إعادة حساب الخوارزميات. لسوء الحظ ، يبدو أن التلاقي يقتصر الآن على حبات 7 × 7 (وهذا لا يكفي بالنسبة لي ، ولكن يكفي لكثير من الاستخدامات).

لم أحاول ربط Haskell OpenCV. يجب أن يكونوا سريعًا ، لأن OpenCV سريعًا حقًا ، لكنني لست متأكدًا مما إذا كانت الروابط كاملة وجيدة بما يكفي لاستخدامها. أيضا ، OpenCV بطبيعتها أمر حتمي للغاية ، مليئة بالتحديثات المدمرة. أفترض أنه من الصعب تصميم واجهة وظيفية لطيفة وفعالة فوقه. إذا ذهب المرء بطريقة OpenCV ، فمن المحتمل أن يستخدم تمثيل OpenCV في كل مكان ، ويستخدم إجراءات OpenCV للتلاعب بها.

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

بقدر علمي ، فإن صفائف Bools غير المربوطة تعتني بتعبئة وتفريغ متجهات البت. أتذكر النظر في تنفيذ المصفوفات من Bools في المكتبات الأخرى ، ولم أر هذا في مكان آخر.

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

وبصرف النظر عن Vector (والقوائم البسيطة) ، فإن جميع مكتبات الصفائف الأخرى قادرة على تمثيل المصفوفات أو المصفوفات ثنائية الأبعاد. أفترض أنهم يتفادون غير مباشر غير ضروري.

Question

أرغب في معالجة بعض مشاكل معالجة الصور في Haskell. أنا أعمل مع كل من الصور النقطية (bitmap) والصور الملونة مع ملايين البكسل. لدي عدد من الأسئلة:

  1. على أي أساس يجب أن أختار بين Vector.Unboxed و UArray ؟ وهي عبارة عن صفيفات غير محمولين ، ولكن يبدو أن التجريد Vector إلى Vector الإعلان عنه بشكل كبير ، خاصة حول اندماج الحلقات. هل Vector دائما أفضل؟ إذا لم يكن الأمر كذلك ، فمتى يجب علي استخدام أي تمثيل؟

  2. بالنسبة للصور الملونة ، سوف أرغب بتخزين ثلاثة أضعاف من الأعداد الصحيحة من 16 بتة أو ثلاثية الأعداد ذات الفاصلة العائمة أحادية الدقة. لهذا الغرض ، هل يمكن استخدام Vector أو UArray بسهولة؟ المزيد من الأداء؟

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

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

أنا مبرمج وظيفي ولست بحاجة إلى طفرة :-)




هنا توجد مكتبة Haskell لمعالجة الصور الجديدة التي يمكنها التعامل مع جميع المهام المعنية وغير ذلك الكثير. وهو يستخدم حاليًا حزم Repa و Vector للتمثيل الأساسي ، مما Repa الاندماج والحساب المتوازي والطفرة ومعظم الأشياء الأخرى التي تأتي مع تلك المكتبات. يوفر واجهة سهلة الاستخدام تعد أمرًا طبيعيًا للتلاعب بالصور:

  • 2D فهرسة و بكسلات غير Word16 بدقة تعسفية ( Double ، Float ، Word16 ، etc ..)
  • جميع الوظائف الأساسية مثل map ، fold ، zipWith ، traverse ...
  • دعم لمساحات الألوان المختلفة: RGB ، HSI ، المقياس الرمادي ، ثنائي النغمة ، المعقدة ، إلخ.
  • وظائف معالجة الصور الشائعة:
    • مورفولوجيا الثنائية
    • التفاف
    • إقحام
    • تحويل فورييه
    • الرسم البياني الرسم البياني
    • إلخ
  • القدرة على التعامل مع البكسلات والصور كأعداد منتظمة.
  • قراءة وكتابة تنسيقات الصور الشائعة من خلال مكتبة JuicyPixels

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

شيء واحد لا يفعله هو تعبئة عدة بيكسلات ثنائية في Word ، بدلا من ذلك يستخدم Word لكل بكسل ثنائي ، ربما في المستقبل ...