fork download
  1. class Knowledge(private val formula: Long) extends AnyVal {
  2. import Knowledge._
  3.  
  4. def &&(that: Knowledge) = Knowledge(this.formula & that.formula)
  5. def ||(that: Knowledge) = Knowledge(this.formula | that.formula)
  6. def unary_! = Knowledge(~formula)
  7.  
  8. def implies(that: Knowledge) = ((!this || that) == TAUTOLOGY)
  9.  
  10. def frontIsClear = implies(FRONT_IS_CLEAR)
  11. def frontIsBlocked = implies(!FRONT_IS_CLEAR)
  12.  
  13. def leftIsClear = implies(LEFT_IS_CLEAR)
  14. def leftIsBlocked = implies(!LEFT_IS_CLEAR)
  15.  
  16. def backIsClear = implies(BACK_IS_CLEAR)
  17. def backIsBlocked = implies(!BACK_IS_CLEAR)
  18.  
  19. def rightIsClear = implies(RIGHT_IS_CLEAR)
  20. def rightIsBlocked = implies(!RIGHT_IS_CLEAR)
  21.  
  22. def onBeeper = implies(ON_BEEPER)
  23. def noBeeper = implies(!ON_BEEPER)
  24.  
  25. def beeperAhead = implies(BEEPER_AHEAD)
  26. def nothingAhead = implies(!BEEPER_AHEAD)
  27.  
  28. // TODO Can this be improved with bit twiddling?
  29. def moveForward = {
  30. val temp = this && FRONT_IS_CLEAR
  31.  
  32. if (temp.beeperAhead) BACK_IS_CLEAR && ON_BEEPER
  33. else if (temp.nothingAhead) BACK_IS_CLEAR && NO_BEEPER
  34. else BACK_IS_CLEAR
  35. }
  36.  
  37. // see http://p...content-available-to-author-only...a.de/calcperm.php
  38. private def bit_permute_step(x: Long, mask: Long, shift: Int) = {
  39. val t = ((x >>> shift) ^ x) & mask
  40. (x ^ t) ^ (t << shift)
  41. }
  42.  
  43. def turnLeft = {
  44. var x = forgetAhead
  45. x = bit_permute_step(x, 0x2222222222222222L, 1)
  46. x = bit_permute_step(x, 0x0c0c0c0c0c0c0c0cL, 2)
  47. x = bit_permute_step(x, 0x00f000f000f000f0L, 4)
  48. Knowledge(x)
  49. }
  50.  
  51. def turnRight = {
  52. var x = forgetAhead
  53. x = bit_permute_step(x, 0x00aa00aa00aa00aaL, 7)
  54. x = bit_permute_step(x, 0x00cc00cc00cc00ccL, 6)
  55. x = bit_permute_step(x, 0x00f000f000f000f0L, 4)
  56. Knowledge(x)
  57. }
  58.  
  59. def turnAround = {
  60. var x = forgetAhead
  61. x = bit_permute_step(x, 0x0a0a0a0a0a0a0a0aL, 3)
  62. x = bit_permute_step(x, 0x00cc00cc00cc00ccL, 6)
  63. Knowledge(x)
  64. }
  65.  
  66. def pickBeeper = Knowledge(formula >>> 32)
  67.  
  68. def dropBeeper = Knowledge(formula << 32)
  69.  
  70. // see http://p...content-available-to-author-only...a.de/calcperm.php
  71. private def bit_permute_step_simple(x: Long, mask: Long, shift: Long) = {
  72. val t = (x >>> shift) & mask
  73. ((x & mask) << shift) | t
  74. }
  75.  
  76. def forgetAhead = formula | bit_permute_step_simple(formula, 0x0000ffff0000ffffL, 16)
  77.  
  78. override def toString = "%016x".format(formula)
  79. }
  80.  
  81. object Knowledge {
  82. private def apply(x: Long) = new Knowledge(x)
  83.  
  84. val /* */ FRONT_IS_CLEAR = apply(0xaaaaaaaaaaaaaaaaL) // 01...
  85. val /**/ FRONT_IS_BLOCKED = !FRONT_IS_CLEAR
  86. val /* */ LEFT_IS_CLEAR = apply(0xccccccccccccccccL) // 0011...
  87. val /* */ LEFT_IS_BLOCKED = !LEFT_IS_CLEAR
  88. val /* */ BACK_IS_CLEAR = apply(0xf0f0f0f0f0f0f0f0L) // 00001111...
  89. val /* */ BACK_IS_BLOCKED = !BACK_IS_CLEAR
  90. val /* */ RIGHT_IS_CLEAR = apply(0xff00ff00ff00ff00L) // 0000000011111111...
  91. val /**/ RIGHT_IS_BLOCKED = !RIGHT_IS_CLEAR
  92. val /* */ BEEPER_AHEAD = apply(0xffff0000ffff0000L) // 00000000000000001111111111111111...
  93. val /* */ NOTHING_AHEAD = !BEEPER_AHEAD
  94. val /* */ ON_BEEPER = apply(0xffffffff00000000L) // 0000000000000000000000000000000011111111111111111111111111111111...
  95. val /* */ NO_BEEPER = !ON_BEEPER
  96.  
  97. val /* */ TAUTOLOGY = apply(0xffffffffffffffffL)
  98. val /* */ CONTRADICTION = apply(0x0000000000000000L)
  99. }
  100.  
  101. class Detective(semantics: KarelSemantics) {
  102.  
  103. private val visited = new HashSet[Def]
  104. private val postcondition = new HashMap[Def, Knowledge]
  105.  
  106. private var hints = new ArrayBuffer[Diagnostic]
  107.  
  108. private def warnAbout(msg: String, node: Node) {
  109. hints += Diagnostic(node.pos, msg, 2)
  110. }
  111.  
  112. private def stopWithBug(msg: String, node: Node): Knowledge = {
  113. hints += new Diagnostic(node.pos, msg, 1)
  114. CONTRADICTION
  115. }
  116.  
  117. val result: Seq[Diagnostic] = {
  118. semantics.defs.values.foreach(check)
  119. hints.sortWith(_.pos < _.pos)
  120. }
  121.  
  122. private def check(deF: Def): Knowledge = postcondition.getOrElseUpdate(deF, {
  123. if (visited.add(deF)) {
  124. check(deF.body, TAUTOLOGY)
  125. } else {
  126. // TODO How do we deal with recursive calls?
  127. TAUTOLOGY
  128. }
  129. })
  130.  
  131. private def check(block: Block, initial: Knowledge): Knowledge = {
  132. var knowledge = initial
  133. for (statement <- block.statements) {
  134. if (knowledge == CONTRADICTION) {
  135. warnAbout("dead code", statement)
  136. return CONTRADICTION
  137. }
  138. knowledge = check(statement, knowledge)
  139. }
  140. knowledge
  141. }
  142.  
  143. private def check(statement: Statement, above: Knowledge): Knowledge = statement match {
  144.  
  145. case x @ Call("moveForward") =>
  146. if (above implies FRONT_IS_BLOCKED) stopWithBug("cannot move through wall", x)
  147. else above.moveForward
  148.  
  149. case Call("turnLeft") =>
  150. above.turnLeft
  151. case Call("turnAround") =>
  152. above.turnAround
  153. case Call("turnRight") =>
  154. above.turnRight
  155.  
  156. case x @ Call("pickBeeper") =>
  157. if (above implies NO_BEEPER) stopWithBug("there is no beeper to pick", x)
  158. else above.pickBeeper
  159.  
  160. case x @ Call("dropBeeper") =>
  161. if (above implies ON_BEEPER) stopWithBug("cannot drop another beeper", x)
  162. else above.dropBeeper
  163.  
  164. // TODO How do we deal with preconditions?
  165. // Should we simply check each function again for each client?
  166. // That would probably require a static "stack trace" to be readable.
  167. // TODO Recursive functions yield TAUTOLOGY as of now;
  168. // Can we do better for tail-recursive functions?
  169. case Call(target) => check(semantics.defs(target))
  170.  
  171. case x @ IfThen(condition, th3n) =>
  172. val p = learn(condition)
  173. if (above implies p) {
  174. warnAbout("condition is always true", x)
  175. check(th3n, above)
  176. } else if (above implies !p) {
  177. warnAbout("condition is always false", x)
  178. above
  179. } else {
  180. check(th3n, above && p) || (above && !p)
  181. }
  182.  
  183. case x @ IfThenElse(condition, th3n, e1se) =>
  184. val p = learn(condition)
  185. if (above implies p) {
  186. warnAbout("condition is always true", x)
  187. check(th3n, above)
  188. } else if (above implies !p) {
  189. warnAbout("condition is always false", x)
  190. check(e1se, above)
  191. } else {
  192. check(th3n, above && p) || check(e1se, above && !p)
  193. }
  194.  
  195. case x @ While(condition, body) =>
  196. val p = learn(condition)
  197. if (above implies !p) {
  198. warnAbout("loop is never entered", x)
  199. above
  200. } else {
  201. if (check(body, p) implies p) stopWithBug("infinite loop", x)
  202. else !p // TODO Do we know anything else besides !p below the loop?
  203. }
  204.  
  205. case Repeat(times, body) =>
  206. Stream.iterate(above)(check(body, _)).drop(times).head
  207. }
  208.  
  209. private def learn(condition: Condition): Knowledge = condition match {
  210.  
  211. case False() => CONTRADICTION
  212. case True() => TAUTOLOGY
  213.  
  214. case OnBeeper() => ON_BEEPER
  215. case BeeperAhead() => BEEPER_AHEAD
  216. case FrontIsClear() => FRONT_IS_CLEAR
  217. case LeftIsClear() => LEFT_IS_CLEAR
  218. case RightIsClear() => RIGHT_IS_CLEAR
  219.  
  220. case Not(_, p) => !learn(p)
  221. case Conjunction(p, _, q) => learn(p) && learn(q)
  222. case Disjunction(p, _, q) => learn(p) || learn(q)
  223. case Parenthesized(p) => learn(p)
  224. }
  225. }
  226.  
Compilation error #stdin compilation error #stdout 0s 0KB
stdin
Standard input is empty
compilation info
/opt/scala/bin/scalac: line 50: /dev/null: Permission denied
Main.scala:1: error: value class needs to have a publicly accessible val parameter
class Knowledge(private val formula: Long) extends AnyVal {
                            ^
Main.scala:101: error: not found: type KarelSemantics
class Detective(semantics: KarelSemantics) {
                           ^
Main.scala:103: error: not found: type HashSet
  private val visited = new HashSet[Def]
                            ^
Main.scala:104: error: not found: type HashMap
  private val postcondition = new HashMap[Def, Knowledge]
                                  ^
Main.scala:106: error: not found: type ArrayBuffer
  private var hints = new ArrayBuffer[Diagnostic]
                          ^
Main.scala:108: error: not found: type Node
  private def warnAbout(msg: String, node: Node) {
                                           ^
Main.scala:112: error: not found: type Node
  private def stopWithBug(msg: String, node: Node): Knowledge = {
                                             ^
Main.scala:114: error: not found: value CONTRADICTION
    CONTRADICTION
    ^
Main.scala:117: error: not found: type Diagnostic
  val result: Seq[Diagnostic] = {
                  ^
Main.scala:122: error: not found: type Def
  private def check(deF: Def): Knowledge = postcondition.getOrElseUpdate(deF, {
                         ^
Main.scala:131: error: not found: type Block
  private def check(block: Block, initial: Knowledge): Knowledge = {
                           ^
Main.scala:143: error: not found: type Statement
  private def check(statement: Statement, above: Knowledge): Knowledge = statement match {
                               ^
Main.scala:145: error: not found: value Call
    case x @ Call("moveForward") =>
             ^
Main.scala:146: error: not found: value FRONT_IS_BLOCKED
      if (above implies FRONT_IS_BLOCKED) stopWithBug("cannot move through wall", x)
                        ^
Main.scala:149: error: not found: value Call
    case Call("turnLeft") =>
         ^
Main.scala:151: error: not found: value Call
    case Call("turnAround") =>
         ^
Main.scala:153: error: not found: value Call
    case Call("turnRight") =>
         ^
Main.scala:156: error: not found: value Call
    case x @ Call("pickBeeper") =>
             ^
Main.scala:157: error: not found: value NO_BEEPER
      if (above implies NO_BEEPER) stopWithBug("there is no beeper to pick", x)
                        ^
Main.scala:160: error: not found: value Call
    case x @ Call("dropBeeper") =>
             ^
Main.scala:161: error: not found: value ON_BEEPER
      if (above implies ON_BEEPER) stopWithBug("cannot drop another beeper", x)
                        ^
Main.scala:169: error: not found: value Call
    case Call(target) => check(semantics.defs(target))
         ^
Main.scala:171: error: not found: value IfThen
    case x @ IfThen(condition, th3n) =>
             ^
Main.scala:209: error: not found: type Condition
  private def learn(condition: Condition): Knowledge = condition match {
                               ^
Main.scala:172: error: not found: value condition
      val p = learn(condition)
                    ^
Main.scala:175: error: not found: value th3n
        check(th3n, above)
              ^
Main.scala:180: error: not found: value th3n
        check(th3n, above && p) || (above && !p)
              ^
Main.scala:183: error: not found: value IfThenElse
    case x @ IfThenElse(condition, th3n, e1se) =>
             ^
Main.scala:184: error: not found: value condition
      val p = learn(condition)
                    ^
Main.scala:187: error: not found: value th3n
        check(th3n, above)
              ^
Main.scala:190: error: not found: value e1se
        check(e1se, above)
              ^
Main.scala:192: error: not found: value th3n
        check(th3n, above && p) || check(e1se, above && !p)
              ^
Main.scala:195: error: not found: value While
    case x @ While(condition, body) =>
             ^
Main.scala:196: error: not found: value condition
      val p = learn(condition)
                    ^
Main.scala:201: error: not found: value body
        if (check(body, p) implies p) stopWithBug("infinite loop", x)
                  ^
Main.scala:205: error: not found: value Repeat
    case Repeat(times, body) =>
         ^
Main.scala:206: error: not found: value body
      Stream.iterate(above)(check(body, _)).drop(times).head
                                  ^
Main.scala:211: error: not found: value False
    case False() => CONTRADICTION
         ^
Main.scala:211: error: not found: value CONTRADICTION
    case False() => CONTRADICTION
                    ^
Main.scala:212: error: not found: value True
    case True() => TAUTOLOGY
         ^
Main.scala:212: error: not found: value TAUTOLOGY
    case True() => TAUTOLOGY
                   ^
Main.scala:214: error: not found: value OnBeeper
    case OnBeeper() => ON_BEEPER
         ^
Main.scala:214: error: not found: value ON_BEEPER
    case OnBeeper() => ON_BEEPER
                       ^
Main.scala:215: error: not found: value BeeperAhead
    case BeeperAhead() => BEEPER_AHEAD
         ^
Main.scala:215: error: not found: value BEEPER_AHEAD
    case BeeperAhead() => BEEPER_AHEAD
                          ^
Main.scala:216: error: not found: value FrontIsClear
    case FrontIsClear() => FRONT_IS_CLEAR
         ^
Main.scala:216: error: not found: value FRONT_IS_CLEAR
    case FrontIsClear() => FRONT_IS_CLEAR
                           ^
Main.scala:217: error: not found: value LeftIsClear
    case LeftIsClear() => LEFT_IS_CLEAR
         ^
Main.scala:217: error: not found: value LEFT_IS_CLEAR
    case LeftIsClear() => LEFT_IS_CLEAR
                          ^
Main.scala:218: error: not found: value RightIsClear
    case RightIsClear() => RIGHT_IS_CLEAR
         ^
Main.scala:218: error: not found: value RIGHT_IS_CLEAR
    case RightIsClear() => RIGHT_IS_CLEAR
                           ^
Main.scala:220: error: not found: value Not
    case Not(_, p) => !learn(p)
         ^
Main.scala:220: error: not found: value p
    case Not(_, p) => !learn(p)
                             ^
Main.scala:221: error: not found: value Conjunction
    case Conjunction(p, _, q) => learn(p) && learn(q)
         ^
Main.scala:221: error: not found: value p
    case Conjunction(p, _, q) => learn(p) && learn(q)
                                       ^
Main.scala:222: error: not found: value Disjunction
    case Disjunction(p, _, q) => learn(p) || learn(q)
         ^
Main.scala:222: error: not found: value p
    case Disjunction(p, _, q) => learn(p) || learn(q)
                                       ^
Main.scala:223: error: not found: value Parenthesized
    case Parenthesized(p) => learn(p)
         ^
Main.scala:223: error: not found: value p
    case Parenthesized(p) => learn(p)
                                   ^
59 errors found
spoj: The program compiled successfully, but Main.class was not found.
      Class Main should contain method: def main(args: Array[String]).
stdout
Standard output is empty