لعب Code Golf: ضغط الكود وتقديمه إلى مسابقة AtCoder Platform

مرحبا هبر! أقدم انتباهكم إلى ترجمة المقال " 【コ ー ド ゴ ル フ】 コ ー ド انكماش 圧 縮 し て AtCoder に 提出 す る 【圧 縮 ゴ ル フ】 ".



هل سمعت من قبل عن Code Golf ؟ إنها تشبه لعبة حيث يحاول الجميع كتابة كود معين بأقل عدد ممكن من الأحرف.



تم انتقاد أحد الحلول (كود 171 بايت) الذي تم تحميله لمسابقة AtCoder * على نطاق واسع ، لذلك قررت أن أعرف ما هي المشكلة.



(ملاحظة المترجم: AtCoder هي عبارة عن منصة حيث يتم إجراء مسابقات مختلفة بين المطورين. بناءً على مجال .jp ، النظام الأساسي ياباني ، ولكن هناك مستخدمون من جميع أنحاء العالم. على سبيل المثال ، في وقت ترجمة هذه المقالة ، كان هناك 3 مستخدمين من روسيا في الجزء العلوي من الموقع.)



ضغط الكود



كما أفهمها ، فإن ضغط الكود (= تقليل حجمه - وزنه) يقصره رمزياً. قد يقول المرء أن أعضاء Code Golf يضعون أرواحهم في تقليل كل شخصية وكل بايت. وبما أن الهدف من هذه المسابقة هو كتابة أقصر رمز ممكن ، فلا يوجد سبب لعدم ضغطه.



ألق نظرة على الكود التالي أولاً.



#!ruby -Knrzlib
eval Zlib.inflate'x = Q
  D  OS c

]r       ݳ By 
                  O{4 .  i aQ(`}cB   I2e ߣ  IeT јL>      )u, p S W  H~. , :
z:Ӊ  g O7ʲ  vQ 1h ^<    =& \u7'


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



#!ruby -Knrzlib


إنه shebang وله -Kn و -rzlib المحدد كخيارات سطر أوامر.



يشير -Kn إلى أنه يجب معاملة الكود المكتوب على أنه رمز ثنائي بدون أحرف. على سبيل المثال ، #coding: binary يقوم بنفس الشيء.



-rzlib - مطلوب من قبل مكتبة زليب. اختصار لعبارة "zlib".



eval Zlib.inflate'…


السطر التالي.



Zlib.inflate هي طريقة لفك الشفرة المضغوطة. نظرًا لأنك ترى أنه لا يزال هناك سطر بعد الحرف "، فإننا نتفهم أن هذا الجزء من الكود يفك الشفرة المضغوطة ويطبق تقييمًا عليها.



سأحاول ذلك بنفسي



اعتقدت أنه سيكون من الجيد إنشاء قالب ضغط التعليمات البرمجية.



يتطلب ذلك ثلاث خطوات: 1) كتابة الكود ، 2) ضغط الكود ، 3) إنتاج الكود النهائي. في المقابل ، يجب تكرار الخطوتين 1 و 2 لتقليل نسبة الضغط.



كتابة الكود



دعنا نكتب الكود أولا. (حسنًا ، هذه الخطوة لا تبشر بالخير)



puts [6484,a=?+,0,1,3,?<,2,3,3]+[0,1].map{|x|[a,x,3,x]+(0..29).map{v=x+4;u=x*60+9+_1;[a,v,v,v,a,v,3,6,*[a,6,6,6]*(29-_1),?<,6,x,u,a,v,u,v]}}+(0..59).map{|t|[a,2,2,2]+(0...t).map{[a,8+t-_1,69+_1,5,?<,3,5,6,a,2,6,2]}}


طول هذا الرمز 216 بايت.



الآن دعونا نحاول الضغط.



ضغط



باستخدام هذا البرنامج النصي ، تمكنت من تصغيره إلى 194 بايت!



$ ruby deflate.rb agc047_e.rb > agc047_e.min.rb
194 B


أرسل إلى AtCoder



ضغطت الرمز وأردت إرساله ، لكن كانت هناك مشكلة واحدة.



لسوء الحظ ، لا يمكنني نسخ هذا الرمز ولصقه وإرساله كما هو. الكود الناتج عن الضغط ثنائي. ومع ذلك ، فإن شاشة إرسال AtCoder هي UTF-8. في معظم الأحيان ، تحتوي التعليمات البرمجية المضغوطة على سلاسل بايت غير صالحة في UTF-8 ، لذلك إذا قمت بنسخها ولصقها كما هي ، فسيتم تشويشها.



لذلك سوف أنشر كود URI المشفر مباشرة باستخدام DevTools.



لنفتح شاشة الإرسال ونطلق DevTools. نحتفظ بصفحة تقديم الحل للمسابقة مفتوحة.







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



حدد الطلب المسمى "إرسال" وانقر فوقه بزر الماوس الأيمن ، واضغط على نسخ ، ثم نسخ كجلب.







افتح وحدة التحكم الخاصة بك والصق الرمز الذي نسخته للتو.







لصق بعد sourceCode = كود URI المشفر لدينا (غير معروض في لقطة الشاشة). نحن نستخدم هذا البرنامج النصي لترميز URI . (حفظ باسم deflate-uriencode.rb)



$ ruby deflate-uriencode.rb agc047_e.rb
194 B
%23%21ruby+-Knrzlib%0Aeval+Zlib.inflate%27x%DA-%8DQ%0A%830%10D%AF%D2Ou%B7A%13%5D%14%2B%1E%24%04%C9%01%0AB%13%094%B9%7Bwc%99%8F%81%99%E1%CD%19%C3%E7ai%9CG%F4%DB%0E%D8%E3%80%06%F7%17j6%E3%C0r%E0%D4%DB%9F%DF%9C%B2%F5%988N%0E%9A%5E%29%BD%B4%B5%B8%B6%04%E3%1A%B7%D4Q%0F%0B%1C%C3%CA%BB%ABJ%DC+a%C7%09%89%5C%D7%E8%E5y%0C%AD%5C%10%D3b%DDD%BC%5C%29%95%3A%FD%A99%C8%9D%16%DDw*%DC%05%A73%04f+%C9%19N%822l%84%B2%DE%97%F2%03%93%919%B0%DE%97%F2%03%93%919%B0%27


تحويل agc047_e.rb إلى deflate-uriencode.rb.



من السطر الثاني للإخراج ، انسخ كل شيء بعد٪ 23 والصقه بعد رمز المصدر أعلاه =.







الآن يمكننا تقديم حلنا.



تغيير الكود (جعله أقصر)



لنختصر الكود. هناك طريقتان لتقصير الكود بعد الضغط.



  • تقليص شفرة المصدر
  • زيادة نسبة الضغط


سأحاول استخدام كلتا الطريقتين. يعد تقليص شفرة المصدر طريقة مفضلة للمساهمين في Code Golf.



زيادة نسبة الضغط



كيف يمكنني زيادة نسبة الضغط؟ نستخدم الآن ضغط Deflate ، وهو مزيج من ضغط طول التشغيل وترميز Huffman. انتبه إلى كود هوفمان هذا. يختلف كود هوفمان من حيث أن نسبة الضغط تزداد مع انخفاض الإنتروبيا قبل الضغط. يتناقص الانتروبيا مع تحول احتمالات ظهور الكود. لذلك ، إذا تم تغيير احتمال حدوث الرموز ، فستزيد نسبة الضغط مع حدوث التحول.



طريقة فعالة لتقليل احتمالية ظهور الكود هو تقليل نوع الحرف. للقيام بذلك ، يمكنك إعادة تسمية المتغير.



في الكود الأول ، دعنا نعيد تسمية المتغيرين x و v إلى t و p. بعد ذلك ، نظرًا لأنه يتم وضعه مع وضع اسم الوظيفة أو الخريطة ، يمكن تقليل نوع الحرف.



puts [6484,a=?+,0,1,3,?<,2,3,3]+[0,1].map{|t|[a,t,3,t]+(0..29).map{p=t+4;u=t*60+9+_1;[a,p,p,p,a,p,3,6,*[a,6,6,6]*(29-_1),?<,6,t,u,a,p,u,p]}}+(0..59).map{|t|[a,2,2,2]+(0...t).map{[a,8+t-_1,69+_1,5,?<,3,5,6,a,2,6,2]}}


$ ruby deflate.rb agc047_e.rb > agc047_e.min.rb
275 B


حسنًا ، لقد زاد.



أزل p واستبدله بـ s.



puts [6484,a=?+,0,1,3,?<,2,3,3]+[0,1].map{|t|[a,t,3,t]+(0..29).map{s=t+4;u=t*60+9+_1;[a,s,s,s,a,s,3,6,*[a,6,6,6]*(29-_1),?<,6,t,u,a,s,u,s]}}+(0..59).map{|t|[a,2,2,2]+(0...t).map{[a,8+t-_1,69+_1,5,?<,3,5,6,a,2,6,2]}}


$ ruby deflate.rb agc047_e.rb > agc047_e.min.rb
184 B


هذه المرة يتقلص بشكل صحيح.



(لا أعرف لماذا زاد ، لذا من فضلك ، إذا كان هناك من يعرف ، أخبرنا).

وهكذا ، من خلال التجربة والخطأ ، تمكنا من تقصير الكود.



الرابط الأصلي لهذه المقالة موجود هنا



وسنكون سعداء للغاية إذا أخبرتنا ما إذا كنت قد أحببت هذه المقالة ، هل كانت الترجمة واضحة ، هل كانت مفيدة لك؟



All Articles