package Ġnl . j ste ge . ad vent of code . a oc common . utils Ċ Ċ import Ġkotlin . math . abs Ċ Ċ /** Ċ Ġ* ĠRepresents Ġa Ġpoint Ġwith Ġa Ġx Ġand Ġan Ġy Ġvalue . ĠThis Ġclass Ġis Ġimmutable . ĠAny Ċ Ġ* Ġaddition Ġor Ġsub traction Ġwill Ġresult Ġin Ġa Ġnew Ġ[ Point ] Ġobject . Ċ Ġ* Ġ@ author ĠJ elle ĠSte ge Ċ Ġ* Ċ Ġ* Ġ@ property Ġx ĠThe Ġx Ġvalue Ġfor Ġthis Ġpoint . Ċ Ġ* Ġ@ property Ġy ĠThe ĠY Ġvalue Ġfor Ġthis Ġproperty . Ċ Ġ* Ċ Ġ* Ġ@ constructor ĠInitializes Ġa Ġ[ Point ] Ġfor Ġthe Ġgiven Ġx Ġand Ġy Ġcoordinates . Ċ Ġ*/ Ċ data Ġclass ĠPoint Ġinternal Ġconstructor ( val Ġx : ĠInt , Ġval Ġy : ĠInt ) Ġ: ĠComparable < Point > Ġ{ ĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠDefines Ġsome Ġconstants Ġand Ġsome Ġbuilder Ġfunctions . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġcompanion Ġobject Ġ{ ĊĠĠĠĠĠĠĠ Ġ/** ĊĠĠĠĠĠĠĠĠ Ġ* ĠRepresents Ġa Ġorigin Ġof Ġ( 0 , 0 ) ĊĠĠĠĠĠĠĠĠ Ġ*/ ĊĠĠĠĠĠĠĠ Ġval ĠZERO _ ZERO Ġ= ĠPoint . of ( 0 , Ġ 0 ) ĊĊĠĠĠĠĠĠĠ Ġ/** ĊĠĠĠĠĠĠĠĠ Ġ* ĠRepresents Ġa Ġcoordinate Ġat Ġ( 1 , 1 ) ĊĠĠĠĠĠĠĠĠ Ġ*/ ĊĠĠĠĠĠĠĠ Ġval ĠONE _ ONE Ġ= ĠPoint . of ( 1 , Ġ 1 ) ĊĊĠĠĠĠĠĠĠ Ġ/** ĊĠĠĠĠĠĠĠĠ Ġ* ĠCreates Ġa Ġ[ Point ] Ġof Ġthe Ġgiven Ġx Ġand Ġy Ġvalues . ĊĠĠĠĠĠĠĠĠ Ġ* ĊĠĠĠĠĠĠĠĠ Ġ* Ġ@ param Ġx ĠThe Ġx Ġvalue Ġto Ġuse . ĊĠĠĠĠĠĠĠĠ Ġ* Ġ@ param Ġy ĠThe Ġy Ġvalue Ġto Ġuse . ĊĠĠĠĠĠĠĠĠ Ġ* Ġ@ return ĠA Ġnew Ġpoint Ġwith Ġcorresponding Ġx Ġand Ġy Ġvalues . ĊĠĠĠĠĠĠĠĠ Ġ*/ ĊĠĠĠĠĠĠĠ Ġfun Ġof ( x : ĠInt , Ġy : ĠInt ) Ġ= ĠPoint ( x , Ġy ) ĊĊĠĠĠĠĠĠĠ Ġ/** ĊĠĠĠĠĠĠĠĠ Ġ* ĠCreates Ġa Ġ[ List ] Ġof Ġ[ Point ] s Ġfor Ġthe Ġgiven Ġranges . ĊĠĠĠĠĠĠĠĠ Ġ* ĊĠĠĠĠĠĠĠĠ Ġ* Ġ@ param Ġxs ĠThe Ġx Ġvalues Ġto Ġuse . ĊĠĠĠĠĠĠĠĠ Ġ* Ġ@ param Ġys ĠThe Ġy Ġvalues Ġto Ġuse . ĊĠĠĠĠĠĠĠĠ Ġ* Ġ@ return ĠA Ġ[ List ] Ġof Ġ[ Point ] s Ġfor Ġthe Ġgiven Ġranges . ĊĠĠĠĠĠĠĠĠ Ġ*/ ĊĠĠĠĠĠĠĠ Ġfun Ġof ( xs : ĠInt Progress ion , Ġys : ĠInt Progress ion ) Ġ= ĊĠĠĠĠĠĠĠĠĠĠĠ Ġys . flatMap Ġ{ Ġy Ġ-> Ġxs . map Ġ{ Ġx Ġ-> ĠPoint . of ( x , Ġy ) Ġ} Ġ} ĊĊĠĠĠĠĠĠĠ Ġfun Ġof ( from : ĠPoint , Ġto : ĠPoint ) Ġ= ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ( from . x .. to . x ). as Sequence (). flatMap Ġ{ Ġx Ġ-> ĊĠĠĠĠĠĠĠĠĠĠĠĠĠĠĠ Ġ( from . y .. to . y ). as Sequence (). map Ġ{ Ġy Ġ-> ĠPoint . of ( x , Ġy ) Ġ} ĊĠĠĠĠĠĠĠĠĠĠĠ Ġ} ĊĊĠĠĠĠĠĠĠ Ġ/** ĊĠĠĠĠĠĠĠĠ Ġ* ĠCreates Ġa Ġ[ Point ] Ġof Ġthe Ġgiven Ġ[ Pair ], Ġusing Ġthe Ġfirst Ġvalue ĊĠĠĠĠĠĠĠĠ Ġ* Ġas Ġx Ġand Ġthe Ġsecond Ġvalue Ġas Ġy . ĊĠĠĠĠĠĠĠĠ Ġ* ĊĠĠĠĠĠĠĠĠ Ġ* Ġ@ param Ġp ĠThe Ġpair Ġto Ġconvert Ġto Ġa Ġ[ Point ] ĊĠĠĠĠĠĠĠĠ Ġ* Ġ@ return ĠA Ġnew Ġpoint Ġwith Ġcorresponding Ġx Ġand Ġy Ġvalues . ĊĠĠĠĠĠĠĠĠ Ġ*/ ĊĠĠĠĠĠĠĠ Ġfun Ġof ( p : ĠPair < Int , ĠInt >) Ġ= ĠPoint ( p . first , Ġp . second ) ĊĊĠĠĠĠĠĠĠ Ġprivate Ġval ĠNE IGH B ORS 8 Ġ= Ġset Of ( ĊĠĠĠĠĠĠĠĠĠĠĠ ĠPoint . of (- 1 , Ġ- 1 ), ĠPoint . of ( 0 , Ġ- 1 ), ĠPoint . of ( 1 , Ġ- 1 ), ĊĠĠĠĠĠĠĠĠĠĠĠ ĠPoint . of (- 1 , Ġ 0 ), ĠPoint . of ( 1 , Ġ 0 ), ĊĠĠĠĠĠĠĠĠĠĠĠ ĠPoint . of (- 1 , Ġ 1 ), ĠPoint . of ( 0 , Ġ 1 ), ĠPoint . of ( 1 , Ġ 1 ) ĊĠĠĠĠĠĠĠ Ġ) ĊĊĠĠĠĠĠĠĠ Ġprivate Ġval ĠNE IGH B ORS 4 Ġ= Ġset Of ( ĊĠĠĠĠĠĠĠĠĠĠĠ ĠPoint . of ( 0 , Ġ- 1 ), ĠPoint . of (- 1 , Ġ 0 ), ĠPoint . of ( 1 , Ġ 0 ), ĠPoint . of ( 0 , Ġ 1 ) ĊĠĠĠĠĠĠĠ Ġ) ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠAll Ġadj ec ent Ġ[ Point ] s , Ġincludes Ġthe Ġ 4 Ġor thogonal Ġand Ġ 4 Ġdiagonal Ġdirections . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġval Ġneighbors 8 : ĠSet < Point > Ġby Ġlazy Ġ{ ĠNE IGH B ORS 8 . map Ġ{ Ġthis Ġ+ Ġit Ġ}. toSet () Ġ} ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠAll Ġadj ec ent Ġ[ Point ] s Ġwithout Ġdiag on als , Ġthus Ġonly Ġthe Ġ 4 Ġor thogonal Ġdirections . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġval Ġneighbors 4 : ĠSet < Point > Ġby Ġlazy Ġ{ ĠNE IGH B ORS 4 . map Ġ{ Ġthis Ġ+ Ġit Ġ}. toSet () Ġ} ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠReturns Ġthe Ġpoint Ġbased Ġoff Ġthe Ġ[ Direction ] Ġgiven ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġmove Direction ( direction : ĠDirection ) Ġ= Ġthis Ġ+ Ġdirection . mod ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠReturns Ġthe Ġpoint Ġbased Ġoff Ġthe Ġ[ Direction ] Ġgiven , Ġwhich Ġis Ġthe Ġamount Ġof Ġsteps Ġaway . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġmove Direction ( direction : ĠDirection , Ġsteps : ĠInt ) Ġ= Ġthis Ġ+ Ġ( direction . mod Ġ* Ġsteps ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠReturns Ġthe Ġman h att an Ġdistance Ġbetween Ġthis Ġ[ Point ] Ġand Ġthe Ġother Ġ[ Point ] ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġman h att an ( other : ĠPoint ) Ġ= Ġabs ( x Ġ- Ġother . x ) Ġ+ Ġabs ( y Ġ- Ġother . y ) ĊĊĠĠĠ Ġfun Ġarea ( other : ĠPoint ): ĠLong Ġ= Ġabs ( x . to Long () Ġ- Ġother . x ) Ġ* Ġabs ( y Ġ- Ġother . y ) ĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠAdds Ġsome Ġvalues Ġto Ġthe Ġx Ġand Ġy Ġvalues Ġof Ġthis Ġpoint . ĊĠĠĠĠ Ġ* ĠResults Ġin Ġa Ġnew Ġpoint . ĊĠĠĠĠ Ġ* Ġ@ param Ġax ĠThe Ġvalue Ġto Ġadd Ġto Ġthe Ġx Ġvalue Ġof Ġthis Ġpoint . ĊĠĠĠĠ Ġ* Ġ@ param Ġay Ġthe Ġvalue Ġto Ġadd Ġto Ġthe Ġy Ġvalue Ġof Ġthis Ġpoint . ĊĠĠĠĠ Ġ* Ġ@ return ĠA Ġnew Ġ[ Point ] Ġwith Ġthe Ġnew Ġvalues . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġadd ( ax : ĠInt , Ġay : ĠInt ) Ġ= ĠPoint . of ( x Ġ+ Ġax , Ġy Ġ+ Ġay ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠAdds Ġtwo Ġpoints , Ġresults Ġin Ġa Ġnew Ġobject . ĊĠĠĠĠ Ġ* Ġ@ param Ġp Ġthe Ġpoint Ġto Ġadd . ĊĠĠĠĠ Ġ* Ġ@ return ĠA Ġnew Ġ[ Point ] Ġwith Ġthe Ġnew Ġvalues . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġadd ( p : ĠPoint ) Ġ= Ġadd ( p . x , Ġp . y ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠAdds Ġa Ġvalue Ġto Ġthe Ġx Ġvalue Ġof Ġthis Ġpoint . ĠResults Ġin Ġa Ġnew Ġobject . ĊĠĠĠĠ Ġ* Ġ@ param Ġax Ġthe Ġvalue Ġto Ġadd Ġto Ġthe Ġx Ġvalue Ġof Ġthis Ġpoint . ĊĠĠĠĠ Ġ* Ġ@ return ĠA Ġnew Ġ[ Point ] Ġwith Ġthe Ġnew Ġvalues . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġadd X ( ax : ĠInt ) Ġ= Ġadd ( ax , Ġ 0 ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠAdds Ġa Ġvalue Ġto Ġthe Ġy Ġvalue Ġof Ġthis Ġpoint . ĠResults Ġin Ġa Ġnew Ġobject . ĊĠĠĠĠ Ġ* Ġ@ param Ġay Ġthe Ġvalue Ġto Ġadd Ġto Ġthe Ġy Ġvalue Ġof Ġthis Ġpoint . ĊĠĠĠĠ Ġ* Ġ@ return ĠA Ġnew Ġ[ Point ] Ġwith Ġthe Ġnew Ġvalues . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġadd Y ( ay : ĠInt ) Ġ= Ġadd ( 0 , Ġay ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠIn crements Ġthe Ġx Ġvalue Ġof Ġthis Ġpoint Ġby Ġ 1 . ĠResults Ġin Ġa Ġnew Ġobject . ĊĠĠĠĠ Ġ* Ġ@ return ĠA Ġnew Ġ[ Point ] Ġwith Ġthe Ġnew Ġvalues . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġinc X () Ġ= Ġadd ( 1 , Ġ 0 ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠIn crements Ġthe Ġy Ġvalue Ġof Ġthis Ġpoint Ġby Ġ 1 . ĠResults Ġin Ġa Ġnew Ġobject . ĊĠĠĠĠ Ġ* Ġ@ return ĠA Ġnew Ġ[ Point ] Ġwith Ġthe Ġnew Ġvalues . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġinc Y () Ġ= Ġadd ( 0 , Ġ 1 ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠSubtract s Ġsome Ġvalues Ġfrom Ġthe Ġx Ġand Ġy Ġvalues Ġof Ġthis Ġpoint . ĊĠĠĠĠ Ġ* ĠResults Ġin Ġa Ġnew Ġpoint . ĊĠĠĠĠ Ġ* Ġ@ param Ġsx ĠThe Ġvalue Ġto Ġsubtract Ġfrom Ġthe Ġx Ġvalue Ġof Ġthis Ġpoint . ĊĠĠĠĠ Ġ* Ġ@ param Ġsy Ġthe Ġvalue Ġto Ġsubtract Ġfrom Ġto Ġthe Ġy Ġvalue Ġof Ġthis Ġpoint . ĊĠĠĠĠ Ġ* Ġ@ return ĠA Ġnew Ġ[ Point ] Ġwith Ġthe Ġnew Ġvalues . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġsub ( sx : ĠInt , Ġsy : ĠInt ) Ġ= Ġadd (- sx , Ġ- sy ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠSubtract s Ġtwo Ġpoints , Ġresults Ġin Ġa Ġnew Ġobject . ĊĠĠĠĠ Ġ* Ġ@ param Ġp Ġthe Ġpoint Ġto Ġsubtract . ĊĠĠĠĠ Ġ* Ġ@ return ĠA Ġnew Ġ[ Point ] Ġwith Ġthe Ġnew Ġvalues . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġsub ( p : ĠPoint ) Ġ= Ġsub ( p . x , Ġp . y ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠSubtract s Ġa Ġvalue Ġfrom Ġthe Ġx Ġvalue Ġof Ġthis Ġpoint . ĊĠĠĠĠ Ġ* ĠResults Ġin Ġa Ġnew Ġobject . ĊĠĠĠĠ Ġ* Ġ@ param Ġsx Ġthe Ġvalue Ġto Ġsubtract Ġfrom Ġthe Ġx Ġvalue Ġof Ġthis Ġpoint . ĊĠĠĠĠ Ġ* Ġ@ return ĠA Ġnew Ġ[ Point ] Ġwith Ġthe Ġnew Ġvalues . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġsub X ( sx : ĠInt ) Ġ= Ġsub ( sx , Ġ 0 ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠSubtract s Ġa Ġvalue Ġfrom Ġthe Ġy Ġvalue Ġof Ġthis Ġpoint . ĊĠĠĠĠ Ġ* ĠResults Ġin Ġa Ġnew Ġobject . ĊĠĠĠĠ Ġ* Ġ@ param Ġsy Ġthe Ġvalue Ġto Ġsubtract Ġfrom Ġthe Ġy Ġvalue Ġof Ġthis Ġpoint . ĊĠĠĠĠ Ġ* Ġ@ return ĠA Ġnew Ġ[ Point ] Ġwith Ġthe Ġnew Ġvalues . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġsub Y ( sy : ĠInt ) Ġ= Ġsub ( 0 , Ġsy ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠDec re ments Ġthe Ġx Ġvalue Ġof Ġthis Ġpoint Ġby Ġ 1 . ĠResults Ġin Ġa Ġnew Ġobject . ĊĠĠĠĠ Ġ* Ġ@ return ĠA Ġnew Ġ[ Point ] Ġwith Ġthe Ġnew Ġvalues . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġdec X () Ġ= Ġsub ( 1 , Ġ 0 ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠDec re ments Ġthe Ġy Ġvalue Ġof Ġthis Ġpoint Ġby Ġ 1 . ĠResults Ġin Ġa Ġnew Ġobject . ĊĠĠĠĠ Ġ* Ġ@ return ĠA Ġnew Ġ[ Point ] Ġwith Ġthe Ġnew Ġvalues . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġfun Ġdec Y () Ġ= Ġsub ( 0 , Ġ 1 ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠAdds Ġtwo Ġpoints , Ġresults Ġin Ġa Ġnew Ġobject . ĊĠĠĠĠ Ġ* Ġ@ param Ġp Ġthe Ġpoint Ġto Ġadd . ĊĠĠĠĠ Ġ* Ġ@ return ĠA Ġnew Ġ[ Point ] Ġwith Ġthe Ġnew Ġvalues . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġoperator Ġfun Ġplus ( p : ĠPoint ) Ġ= Ġadd ( p ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠSubtract s Ġtwo Ġpoints , Ġresults Ġin Ġa Ġnew Ġobject . ĊĠĠĠĠ Ġ* Ġ@ param Ġp Ġthe Ġpoint Ġto Ġsubtract . ĊĠĠĠĠ Ġ* Ġ@ return ĠA Ġnew Ġ[ Point ] Ġwith Ġthe Ġnew Ġvalues . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġoperator Ġfun Ġminus ( p : ĠPoint ) Ġ= Ġsub ( p ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠPerforms Ġa Ġscalar Ġmultiplication Ġon Ġthis Ġ[ Point ] ĊĠĠĠĠ Ġ* Ġ@ param Ġn ĠThe Ġinteger Ġto Ġmultiply Ġthe Ġpoint Ġwith . ĊĠĠĠĠ Ġ* Ġ@ return Ġa Ġnew Ġ[ Point ] Ġwith Ġthe Ġnew Ġvalues . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġoperator Ġfun Ġtimes ( n : ĠInt ) Ġ= ĠPoint . of ( x Ġ* Ġn , Ġy Ġ* Ġn ) ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠComp ares Ġthis Ġpoint Ġto Ġanother Ġpoint . ĊĠĠĠĠ Ġ* Ġ@ param Ġother ĠThe Ġother Ġpoint . ĊĠĠĠĠ Ġ* Ġ@ return Ġ 0 Ġif Ġthe Ġpoints Ġare Ġequal , Ġ< Ġ 0 Ġif Ġthis Ġpoint Ġis Ġsmaller Ġthan Ġthe Ġother Ġand Ġ> Ġ 0 Ġif ĊĠĠĠĠ Ġ* Ġthis Ġpoint Ġis Ġbigger Ġthan Ġthe Ġother . ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġoverride Ġfun Ġcompare To ( other : ĠPoint ): ĠInt Ġ= Ġwhen Ġ{ ĊĠĠĠĠĠĠĠ Ġthis Ġ=== Ġother Ġ-> Ġ 0 ĊĠĠĠĠĠĠĠ Ġelse Ġ-> Ġx . compareTo ( other . x ). let Ġ{ Ġif Ġ( it Ġ!= Ġ 0 ) Ġit Ġelse Ġy . compareTo ( other . y ) Ġ} ĊĠĠĠ Ġ} ĊĊĠĠĠ Ġ/** ĊĠĠĠĠ Ġ* ĠConverts Ġthis Ġpoint Ġto Ġa ĠString Ġrepresentation . ĊĠĠĠĠ Ġ* Ġ@ return ĠThe ĠString Ġrepresentation Ġfor Ġthis Ġpoint , Ġwhich Ġis Ġof Ġthe Ġtype Ġ( x , Ġy ) ĊĠĠĠĠ Ġ*/ ĊĠĠĠ Ġoverride Ġfun ĠtoString (): ĠString Ġ= Ġ" ($ x ,$ y )" Ċ } Ċ