অভিন্ন টুকরা মধ্যে একটি পিজা কাটা


16

আমি পুরোপুরি এটি পড়ার আগে এই প্রশ্নটি যা হতে ভেবেছিল তা এই

একদল কোড গল্ফরা দ্য নাইনটিথ বাইট পিজ্জারিয়ায় walkুকে পিজ্জার অর্ডার দেয়। এটি ইউনিট স্কোয়ারগুলি দিয়ে তৈরি একটি অনিয়মিত আকারে আসে। আপনার কাজটি হ'ল এটিকে অভিন্ন কাটা কাটাতে সহায়তা করা। অর্থাত, টুকরোগুলির অবশ্যই একই আকার এবং আকার থাকতে হবে; এগুলি ঘোরানো যায় তবে ফ্লিপ / মিরর করা যায় না। উদাহরণস্বরূপ, যদি তারা টেট্রিস টুকরা হয় তবে তাদের অবশ্যই একই ধরণের হতে হবে, আপনি একটি এল টুকরা এবং জে টুকরা উভয়ই ব্যবহার করতে পারবেন না।

ইনপুট

আপনাকে প্রথম লাইনে গ্রুপের লোকদের সংখ্যা দেওয়া হবে (সর্বদা 2 থেকে 10 এর মধ্যে পূর্ণসংখ্যার অন্তর্ভুক্ত) এবং এর পরে '' (স্পেস) এবং '#' অক্ষরের একটি আয়তক্ষেত্রাকার ম্যাট্রিক্স, পিজ্জার প্রতিনিধিত্ব করে। সমস্ত '#' অক্ষর তাদের প্রান্তের মাধ্যমে সংযুক্ত রয়েছে। '#' অক্ষরের সংখ্যাটি মানুষের সংখ্যার একাধিক হওয়ার গ্যারান্টিযুক্ত।

আউটপুট

আপনার একই 'ম্যাট্রিক্স মুদ্রণ করা উচিত, প্রতিটি' # 'অক্ষর 0 থেকে n-1 (n লোকের সংখ্যা হওয়া) এর সাথে একটি অঙ্কের সাথে প্রতিস্থাপিত হবে। প্রতিটি সংখ্যা একটি টুকরা চিহ্নিত করা উচিত। স্লাইস আকারটি অবশ্যই বর্গাকার প্রান্তগুলির মধ্য দিয়ে সংযুক্ত থাকতে হবে। স্লাইস নম্বরটি কোনও নির্দিষ্ট ক্রমে থাকা দরকার নেই। যদি পিজ্জা কাটার একাধিক উপায় থাকে তবে সেগুলির কোনওটি গ্রহণযোগ্য।
যদি প্রয়োজন অনুযায়ী পিজ্জা কাটা সম্ভব না হয় তবে আপনার "পিজ্জা নেই!" স্ট্রিংটি মুদ্রণ করা উচিত! পরিবর্তে.

স্কোরিং

এটি কোড গল্ফ। আপনার স্কোরটি প্রোগ্রামে বাইট সংখ্যা হবে। অক্ষরগুলি তাদের ইউটিএফ -8 এনকোডিংয়ের মাধ্যমে গণনা করা হবে। সর্বনিম্ন স্কোর জয়।

উদাহরণ

ইনপুট:

3
 #  
### 
####
   #

আউটপুট:

 0  
100 
1122
   2

ইনপুট:

4
###
# #
###

আউটপুট:

001
2 1
233

ইনপুট:

2
#    #
######

আউটপুট:

No pizza for you!

ইনপুট:

5
    #  
   ####
  #####
 ##### 
#####  
####   
  #    

আউটপুট:

    0  
   1000
  21110
 32221 
43332  
4443   
  4    

ইনপুট:

4
   #   
 ####  
###### 
  #####
  #### 

আউটপুট:

   0   
 1000  
111203 
  12233
  2233 

আবশ্যকতা

  • আপনার একটি সম্পূর্ণ প্রোগ্রাম লিখতে হবে যা স্ট্যান্ডার্ড ইনপুট থেকে পড়ে এবং স্ট্যান্ডার্ড আউটপুটে লেখবে।
  • লিনাক্সে অবাধে উপলভ্য সফ্টওয়্যার ব্যবহার করে প্রোগ্রামটি চালানো উচিত।
  • আপনার কম্পিউটারের উপরের প্রতিটি উদাহরণ একটি আধুনিক কম্পিউটারে 1 মিনিটেরও কম সময়ে শেষ করা উচিত।
  • কোনও মানক ফাঁক নেই।

3
উনিশতম কামড় : ^)
ফ্রাইআম

@ ফ্রাইআম দ্য এজিগম্যান © ক্যালভিনের শখ
অ্যাডিটসু

রেগেক্স সমাধানের জন্য বোনাস।
flawr

উত্তর:


3

পিএইচপি কোড, 1808 971 বাইট

পিএইচপি দ্রুত এবং নোংরা বাস্তবায়ন implementation প্রথমে সমস্ত সম্ভাব্য স্লাইস আকারগুলি ব্রুটে-ফোর্স করুন, পরবর্তী ব্রুট-ফোর্সের সমস্ত অবস্থান এবং অভিযোজনগুলি।

ব্যবহার: cat pizza.txt | php pizza.php

সম্পাদনা করুন: নেস্টেড লুপগুলির পরিবর্তে পুনরাবৃত্তি ব্যবহার করে অ্যালগরিদম পুনরায় লিখে কোডের আকার 45% এরও বেশি কমান। যাইহোক, এটি মেমরিটি খায় (এবং পিজা এর ;-))। 8x8 এর চেয়ে বড় পিজ্জার স্মৃতি সম্ভবত শেষ হয়ে যাবে। নেস্টেড লুপ ভেরিয়েন্টটি যে কোনও আকারকে সহজেই পরিচালনা করতে পারে তবে কোড আকারের দ্বিগুণ।

<?php define('A',98);$n=fgets(STDIN);$d=array();$m=$u=str_pad('',A,'+');$s=0;while($g=fgets(STDIN)){$g=rtrim($g);assert(strlen($g)<=A-2);$s++;$m.='+'.str_pad(rtrim($g),A-2,' ').'+';for($l=0;$l<strlen($g);$l++)if($g[$l]=='#')$d[]=$s*A+$l+1;}$m.=$u;$r=count($d)/$n;x(reset($d),array(array()),0,0,0,0);die('No pizza for you!');function x($e,$c,$b,$a,$q,$t){global$r,$m,$d;$h=$a*A+$b;if(!in_array($e+$h,$d))return;if(in_array($h,$c[0]))return;$c[0][]=$h;$c[1][]=$b*A-$a;$c[2][]=-$a*A-$b;$c[3][]=-$b*A+$a;if(count($c[0])<$r)do{x($e,$c,$b+1,$a,$b,$a);x($e,$c,$b,$a+1,$b,$a);x($e,$c,$b-1,$a,$b,$a);x($e,$c,$b,$a-1,$b,$a);$v=($b!=$q||$a!=$t);$b=$q;$a=$t;}while($v);else w($c,$m,0,reset($d),0);}function w(&$p,$f,$o,$e,$i){global$n,$d;foreach($p[$i]as$h){$j=$e+$h;if(!isset($f[$j])||$f[$j]!='#')return;$f[$j]=chr(ord('0')+$o);}if(++$o==$n){for($k=A;$k<strlen($f)-A;$k++)if($k%A==A-1)echo PHP_EOL;else if($k%A)echo$f[$k];exit;}foreach($d as$j)for($i=0;$i<4;$i++)w($p,$f,$o,$j,$i);}

অবহেলিত, নথিভুক্ত কোড

নীচে ডকুমেন্টেড, মূল কোড দেওয়া আছে। আমার মানসিক সুস্থতা রাখতে করার জন্য, আমি পূর্ণ সোর্স কোড সঙ্গে কাজ, এবং ভালো বিবৃতি স্ট্রিপ একটি সহজ minifier স্ক্রিপ্ট লিখেছিলেন assert()এবং error_reporting()উপরোক্ত golfed কোড জেনারেট করতে অপ্রয়োজনীয় বন্ধনী, পুনঃনামকরণ ভেরিয়েবল, ফাংশন এবং ধ্রুবক মুছে ফেলুন।

<?php
error_reporting(E_ALL) ;

// Width of each line of pizza shape.
// Constant will be reduced to single character by minifier,
// so the extra cost of the define() will be gained back.
define('WIDTH', 98) ;

// Read number of slices
$nrSlices = fgets(STDIN) ;

// Read pizza shape definition and 
// convert to individual $positionList[]=$y*width+$x and
// linear (1D) $pizzaShape[$y*WIDTH+$x] with protective border around it.
//
// WARNING: assumes maximum pizza width of WIDTH-2 characters!
$positionList = array() ;
$pizzaShape = $headerFooter = str_pad('', WIDTH, '+') ;
$y = 0 ;
while ($line = fgets(STDIN))
{  $line = rtrim($line) ;
   assert(strlen($line) <= WIDTH-2) ;
   $y++ ;
   $pizzaShape .= '+'.str_pad(rtrim($line), WIDTH-2, ' ').'+' ;
   for ($x = 0 ; $x < strlen($line) ; $x++)
   {  if ($line[$x] == '#') $positionList[] = $y*WIDTH + $x+1 ;
   }
}
$pizzaShape .= $headerFooter ;

// Determine size of a slice
$sliceSize = count($positionList)/$nrSlices ;

// Build all possible slice shapes. All shapes start with their first part at 
// the top of the pizza, and "grow" new parts in all directions next to the 
// existing parts. This continues until the slice has the full size. This way
// we end up with all shapes that fit at the top of the pizza.
//
// The shape is defined as the offsets of the parts relative to the base 
// position at the top of the pizza. Offsets are defined as linear offsets in
// the 1-D $pizzaShape string.
//
// For efficiency, we keep track of all four possible rotations while building
// the slice shape.
//
growSlice(reset($positionList), array(array()), 0, 0, 0, 0) ;
die('No pizza for you!') ;

function growSlice($basePosition, $shapeDeltas, $dx, $dy, $prevDx, $prevDy)
{  global $sliceSize, $pizzaShape, $positionList ;

   // Check validity of new position
   // Abort if position is not part of pizza, or 
   // if position is already part of slice
   $delta = $dy*WIDTH + $dx ;
   if (!in_array($basePosition+$delta, $positionList)) return ;
   if (in_array($delta, $shapeDeltas[0])) return ;

   // Add all four rotations to shapeDeltas[]
   $shapeDeltas[0][] = $delta ;
   $shapeDeltas[1][] = $dx*WIDTH - $dy ;
   $shapeDeltas[2][] = -$dy*WIDTH - $dx ;
   $shapeDeltas[3][] = -$dx*WIDTH + $dy ;

   // Have we built a full slice shape?
   if (count($shapeDeltas[0]) < $sliceSize) 
   {  // Grow shape either at current position or at previous position
      do
      {  growSlice($basePosition, $shapeDeltas, $dx+1, $dy,   $dx, $dy) ;
         growSlice($basePosition, $shapeDeltas, $dx,   $dy+1, $dx, $dy) ;
         growSlice($basePosition, $shapeDeltas, $dx-1, $dy,   $dx, $dy) ;
         growSlice($basePosition, $shapeDeltas, $dx,   $dy-1, $dx, $dy) ;
         $retry = ($dx != $prevDx || $dy != $prevDy) ;
         $dx = $prevDx ;
         $dy = $prevDy ;
      } while ($retry) ;
   } else
   {  // Try to cover the entire pizza by translated and rotated instances of
      // the slice shape.
      fitSlice($shapeDeltas, $pizzaShape, 0, reset($positionList), 0) ;
   }
}

function fitSlice(&$shape, $pizza, $id, $basePosition, $rotation)
{  global $nrSlices, $positionList ;

   // Try to fit each part of the slice onto the pizza. If the part falls
   // outsize the pizza, or overlays another slice we reject this position
   // and rotation. If it fits, we mark the $pizza[] with the slice $id.
   foreach ($shape[$rotation] as $delta)
   {  $position = $basePosition + $delta ;
      if (!isset($pizza[$position]) || $pizza[$position] != '#') return ;
      $pizza[$position] = chr(ord('0')+$id) ;
   }

   // If $nrSlices slices have been fitted, we have found a valid solution!
   // In that case, we display the solution and quit.
   if (++$id == $nrSlices)
   {  for ($pos = WIDTH ; $pos < strlen($pizza)-WIDTH ; $pos++)
      {  if ($pos % WIDTH == WIDTH-1) echo PHP_EOL ;
         else if ($pos % WIDTH) echo $pizza[$pos] ;
      }
      exit ;
   }

   // The current slice did fit, but we have still more slices to fit.
   // Try all positions and rotations for the next slice.
   foreach ($positionList as $position)
   {  for ($rotation = 0 ; $rotation < 4 ; $rotation++)
      {  fitSlice($shape, $pizza, $id, $position, $rotation) ;
      }
   }
}

আমি "পিএইচপি মারাত্মক ত্রুটি পেয়েছি: 1 লাইনে পিজা.php- এ _ () পুনরায় ঘোষণা করতে পারি না"
অ্যাডিটসু

@ অ্যাডিটসু: গল্ফযুক্ত সংস্করণে কেবলমাত্র একটি ফাংশন _ () রয়েছে। আপনি কি ঘটনাক্রমে দুবার কোড অনুলিপি করেছেন?
জেসন স্মিথ

ফাইলের আকার 972 তাই আমি মনে করি না কোডটি দুটিবার ফিট হতে পারে। অবারিত কোডটি বিটিডব্লিউ কাজ করছে বলে মনে হচ্ছে :)
অদিতসু

আমি লক্ষ্য করেছি যে আপনার আছে define('_',98), এর সাথে function _কি বিরোধ নেই ? আমি পিএইচপি জানি না তাই আমি বলতে পারি না ...
aditsu

@ অ্যাডিটসু: গল্ফড কোডটি আমার ম্যাকের পিএইচপি 5.4.43 এর সাথে সূক্ষ্মভাবে কাজ করে, তবে এটি প্রদর্শিত হয় _ () অন্যান্য প্ল্যাটফর্মে গেটেক্সটেক্স () এর একটি নাম। পুরোপুরি _ () এড়াতে মিনিফায়ার পরিবর্তন করা হয়েছে।
জেসন স্মিথ
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.