fork download
  1. #!/usr/bin/perl
  2. # your code goes here
  3.  
  4. # "Read line from STDIN, split on whitespace, return list".
  5. # We do it several times, therefore make it a sub:
  6.  
  7. sub i{<>=~/\S+/g}
  8.  
  9. # @b is height-map of city-scape ("array of arrays",
  10. # i.e. array of array references).
  11. # Also, store grid-lines range in @r array for later re-use:
  12.  
  13. @b=map[i],@r=0..<>-1;
  14.  
  15. # Next, things are getting somewhat compressed.
  16. # Let's take them apart and start from the very end.
  17.  
  18. print.1<=>(map{
  19. @a[1,0,2,4,3]=@a;
  20. @b=map{$i=$_;[map$b[$_][$i],@r]}@r;
  21. grep$a[0]
  22. &&($k=(($x=$_)-$a[3])/$a[0])**2<=$k
  23. &&pop[sort map@{$b[$_]}[$x-!!$x,$x],
  24. ($_=$a[4]+$k*$a[1]),$_-/^\d+$/]
  25. >=$a[5]+$k*$a[2]
  26. ,@R=@r
  27. }@a=map$_-shift@v,i,@u=@v=@$_),$/for([i])x<>
  28.  
  29. # Read player coordinates, make anonymous array, duplicate reference
  30. # as many times as there are enemies, return a list:
  31.  
  32. # ([i])x<>
  33.  
  34. # For each element of this list, compare 0.1 with result of some operation
  35. # (on which more later), print result of comparison
  36. # (can be "-1" or "1" here) followed by a newline:
  37.  
  38. # print.1<=>(...),$/for([i])x<>
  39.  
  40. # That "..." operation is a "map" in scalar (because of comparison)
  41. # context, i.e. number of elements in list returned by "map":
  42. # "1" is printed for empty list, "-1" for non-empty.
  43.  
  44. # This "map" arguments are CODE-BLOCK and LIST.
  45. # LIST is result of another "map":
  46.  
  47. # @a=map$_-shift@v,i,@u=@v=@$_
  48.  
  49. # @$_ is dereferencing of "for" loop variable and that's player coordinates.
  50. # "i" returns current enemy coordinates.
  51. # So, what _this_ "map" returns and what's stored (for later re-use)
  52. # in @a array and what's the LIST for "main" map - they are six numbers:
  53.  
  54. # Xe - Xp
  55. # Ye - Yp
  56. # Ze - Zp
  57. # Xp
  58. # Yp
  59. # Zp
  60.  
  61. # i.e. they are differences between enemy and player respective coordinates,
  62. # followed by player coordinates.
  63.  
  64. # The CODE-BLOCK mentioned above:
  65.  
  66. # @a[1,0,2,4,3]=@a;
  67. # @b=map{$i=$_;[map$b[$_][$i],@r]}@r;
  68. # grep$a[0]
  69. # &&($k=(($x=$_)-$a[3])/$a[0])**2<=$k
  70. # &&pop[sort map@{$b[$_]}[$x-!!$x,$x],
  71. # ($_=$a[4]+$k*$a[1]),$_-/^\d+$/]
  72. # >=$a[5]+$k*$a[2]
  73. # ,@R=@r
  74.  
  75. # As you see, the topic variable ($_) of enclosing "map" is _not_ used.
  76. # The whole point was to build @a array, execute CODE-BLOCK two
  77. # (or _any even number_ of) times (6, here), and return list which,
  78. # in turn, is composed of results of "grep" executions in above BLOCK.
  79.  
  80. # Two first lines of this BLOCK are to swap "x y" coordinates.
  81.  
  82. # @a[1,0,2,4,3]=@a;
  83. # @b=map{$i=$_;[map$b[$_][$i],@r]}@r;
  84.  
  85. # With this little trick we can use the same "grep" part to check both
  86. # "x" and "y" grid-lines.
  87. # Because BLOCK is executed even number of times, coordinates will be
  88. # restored to original state by the time we get to the next enemy.
  89.  
  90. # Now to the "grep" part.
  91. # It evaluates some expression for each element of @r array (grid-lines)
  92. # and returns non-empty list if "expression" is TRUE for any grid-line.
  93. # This, in turn, makes "map" return non-empty list i.e. "-1" is printed
  94. # for a given enemy.
  95.  
  96. # It means that the "expression" checks if, for each integer "x"
  97. # in range, the PE ("player-enemy") line is above or below city-scape.
  98.  
  99. # There are 3 boolean sub-expressions, multiplied with logical "and"s.
  100.  
  101. # First,
  102.  
  103. # $a[0]
  104.  
  105. # i.e. only make further checks if Xe != Xp to avoid "division by zero",
  106. # later. The case of Xe == Xp will be checked when we swap coordinates.
  107.  
  108. # Second,
  109.  
  110. # ($k=(($x=$_)-$a[3])/$a[0])**2<=$k
  111.  
  112. # This sub-expression, apart from defining $x and $k variables for later
  113. # re-use, actually checks if current grid-line is in Xe .. Xp range
  114. # (or Xp .. Xe) - i.e. only go to the 3d sub-expression if it is.
  115.  
  116. # Third,
  117.  
  118. # pop[sort map@{$b[$_]}[$x-!!$x,$x],
  119. # ($_=$a[4]+$k*$a[1]),$_-/^\d+$/]
  120. # >=$a[5]+$k*$a[2]
  121.  
  122. # As you see, it finds a maximum value in some LIST
  123.  
  124. # pop[sort LIST]
  125.  
  126. # and compares it to some value. Alphabetical sorting is OK in our case.
  127.  
  128. # The "value" is none other than "z" coordinate on PE line:
  129.  
  130. # $a[5]+$k*$a[2]
  131.  
  132. # And that LIST is a list of up to 4 "buildings" heights, which share
  133. # the same (x,y) point. BTW, "y" is
  134.  
  135. # $_=$a[4]+$k*$a[1]
  136.  
  137. # These comments are getting a bit long. Understanding sub-expressions
  138. # "2" and "3" mentioned above, as well as "swapping" X <-> Y mechanics
  139. # may require some effort, though not very much.
  140.  
  141. # I hope it's clearer now how it all works. All this complexity was only
  142. # introduced for brevity.
  143.  
Success #stdin #stdout 0s 3608KB
stdin
5
0 0 0 0 0
0 0 0 0 0
4 4 4 4 4
0 0 0 0 0
0 0 0 0 0
2.5 0.0 4.0
3
2.5 5.0 0.1
2.5 5.0 5.0
0.0 2.7 4.5
stdout
-1
1
1