Compare commits

...

9 Commits

Author SHA1 Message Date
magical 6704766eba use dict for 'visit' var in day 16
not sure if this is an improvement? it's more or less the same
as the array version
2023-12-19 04:57:53 +00:00
magical ef2711b76f prelude: add ltranspose 2023-12-19 04:54:36 +00:00
magical 7baf6aa596 prelude: add lextract 2023-12-19 04:50:01 +00:00
magical 89dcdeb553 prelude: add an example for transform 2023-12-19 04:49:17 +00:00
magical 3faf36c645 ignore extra samples 2023-12-18 06:40:01 +00:00
magical 578f6e87ac day 18 part 2 2023-12-18 06:37:56 +00:00
magical bf4e88d66f day 18 part 1 2023-12-18 05:20:25 +00:00
magical fe76e83e98 day 17 fix cost calculation
i was accidentally using the previous coordinates to calculate the cost
for each node, which means the A* search was effectively calculating the
cost of the return trip instead of the forward path.
doesn't affect the path at all - the start and end nodes are fixed, so
it doesn't matter whether their costs are included or not - but it does
mean that the cost being returned at the end was off by ((value at end
point) - (value at start point)) compared to the expected value.
2023-12-17 06:42:34 +00:00
magical 14ef33326e day 17 solution
there's a small bug in the cost calculation which will be fixed in the
next commit
2023-12-17 06:26:31 +00:00
11 changed files with 1178 additions and 11 deletions

28
.gitignore vendored
View File

@ -1 +1,29 @@
/cookie
/day09/sample2.in
/day09/sample3.in
/day09/sample4.in
/day09/sample5.in
/day09/sample6.in
/day09/sample7.in
/day09/sample8.in
/day10/sample1.in
/day10/sample2.in
/day10/sample3.in
/day10/sample4.in
/day10/sample5.in
/day10/sample7.in
/day10/sample9.in
/day11/sample2.in
/day11/sample3.in
/day11/sample4.in
/day11/sample5.in
/day12/sample3.in
/day13/sample2.in
/day13/sample3.in
/day14/sample2.in
/day14/sample3.in
/day16/sample2.in
/day16/sample3.in
/day17/sample2.in
/day18/sample2.in
/day18/sample3.in

View File

@ -20,16 +20,16 @@ proc read-input {input} {
proc reset-visited {} {
global visit
array unset visit
set visit [dict create]
}
proc mark-visited {x y d} {
global visit
set v [switch -exact -- $d n {expr 1} s {expr 2} w {expr 4} e {expr 8} default {error "invalid dir '$d'"}]
incr visit($y,$x) 0
set result [expr {($visit($y,$x) & $v) != 0}]
set visit($y,$x) [expr {$visit($y,$x) | $v}]
return $result
dict incr visit $y,$x 0
set old [dict get $visit $y,$x]
dict set visit $y,$x [expr {$old | $v}]
return [expr {($old & $v) != 0}]
}
proc print-visited {} {
@ -39,7 +39,7 @@ proc print-visited {} {
for {set i 0} {$i < $height} {incr i} {
set row {}
for {set j 0} {$j < $width} {incr j} {
if {[info exist visit($i,$j)] && $visit($i,$j)} {
if {[dict exists $visit $i,$j] && [dict get $visit $i,$j]} {
lappend row "#"
} else {
lappend row "."
@ -93,7 +93,7 @@ proc solve {} {
set beams [follow $beams]
}
print-visited
puts [array size visit]
puts [dict size $visit]
}
proc lmax {list} {
@ -125,8 +125,8 @@ proc solve2 {} {
while {[llen $beams] > 0} {
set beams [follow $beams]
}
puts [array size visit]
lappend l [array size visit]
puts [dict size $visit]
lappend l [dict size $visit]
}
puts [lmax $l]
@ -135,7 +135,7 @@ proc solve2 {} {
read-input stdin
puts [array get grid]
puts [follow {0 0 e}]
puts [array get visit]
puts [dict get $visit]
solve
solve2

105
day17/astar.py 100644
View File

@ -0,0 +1,105 @@
from heapq import heappush, heappop
def search(start, is_goal, neighbors, heuristic=None, worst=None):
if heuristic == None:
def heuristic(x):
return 0
if not callable(is_goal):
goal = is_goal
def is_goal(this):
return this == goal
if not isinstance(start, list):
start = [start]
i = 0 # tiebreaker
q = []
for s in start:
i += 1
heappush(q, (heuristic(s), i, s, None))
done = {}
if worst:
best_worst = min(worst(s) for s in start)
while q:
z, _, this, prev = heappop(q)
if this in done:
continue
cost_so_far = z - heuristic(this)
#print(this,z, cost_so_far)
done[this] = (cost_so_far, prev)
if is_goal(this):
print("astar: visited", len(done), "nodes")
print("astar: pending", len(q), "nodes")
# reconsruct the path
n = this
path = []
while n is not None:
path.append(n)
_, n = done[n]
path.reverse()
return cost_so_far, this, path
for c, n in neighbors(this):
c = cost_so_far + c
if n not in done or c < done[n][0]:
h = heuristic(n)
if worst:
if c+h > best_worst:
# if the best possible cost for this node
# is worse than the lowest worst-case cost we've seen
# then don't even bother exploring it
continue
w = worst(n)
if c+w < best_worst:
best_worst = c+w
i += 1
heappush(q, (c+h, i, n, this))
return float('inf'), None, []
def test():
data = [
"aabqponm",
"abcryxxl",
"accszzxk",
"acctuvwj",
"abdefghi",
]
#data = [
# "aabbaaba",
# "abcbaaba",
# "accabcbb",
# "accbbbba",
# "abbbabab",
#]
start = (0,0)
goal = (5,2)
def get(x,y):
return ord(data[y][x])
def neighbors(src):
x,y = src
here = get(x,y)
n = []
def push(x,y):
if 0 <= y < len(data):
if 0 <= x < len(data[y]):
if get(x,y) <= here+1:
n.append((1, (x,y)))
push(x-1, y)
push(x+1,y)
push(x, y-1)
push(x, y+1)
return n
def heuristic(n):
return abs(goal[0] - n[0]) + abs(goal[1] - n[1])
c, _, path = search(start, goal, neighbors, heuristic)
print(*data, sep="\n")
print(*path, sep="\n")
assert c == 31, c
if __name__ == '__main__':
test()

141
day17/input 100644
View File

@ -0,0 +1,141 @@
541325532413154112543324624344224545523462433352343463247775356367644347443563677657343744452636444345256642465244525244265544431245144444221
331414241322155325566365653323365536535625534662334663573476555335357734444677365546643757652664642422365232553435632422462652133234221512215
112554244333323423245642454645423242233656354535646574735346555646776767536545363675664344376545324446564445556565525526354621135153235435355
542134154422331162256546652564242435642355365533543774673455365777557755536655735643465454333776472665655234623522255366242524413124115451453
255251321341123224246525356462642224343225675747637556637674454344574363677445356433635464757763654622224224643632533433452565562111314332341
323422512325314235242263655345522326644277643546736735556435374637543437655333567455673737467355557747324624235426622233354356446132133215154
541534415132425356522655256624346542356354755664376557445744476334744743465536755754336555544636554557737333443224244456235552453253423313145
515553552411263445633352624623665533344334337643473435634547645473665346447473446437553466757655455367463472264425533355633442452453213442124
544214521555643342656232623463353546563633737773445375774334667743475334577363467775435576654463636667756476334523533536656245462245431325552
444435344234254322226534364244465643743553676564764753654766336746655546757334456666436757744355475475363753752322654652363332225633645155434
212254314564226533533534434524557665735744735556577636573746346635443434567673456637573775336347467573445644354564643546236422336444661324543
512413516564664633325622256245356466543343753467665546337365773767564653766657446456356444363564457774376334434756443242324324342343553415431
123353233256452626246523564247633554636547453756573433544433634767734774746646334333454765563334375553346673354374344625323266355556655225412
332255633633636625263535525635667435356665377666744736446636545565764577677455774735573646553437444674337675673667576235366552324234533442215
223515534224455443532343536547353366775533575556634444434737867846787446578668886484577736735663344633473457576544343265455656255646522424132
533546255455524366545365473433534564467543663577337455744574545784658875787488555445786876364433545775774533573546546554333656323556264426531
243536232465655424464653354376357773364566775433766547487787585756455675665875447777646868877576375577734473634775475667446545452346443626462
155623534353226323442675576457657475474357735635687785478546678646666448578775875848665587878733645577643473333467575545543563266636464343253
236332623432542664353547736564656564374753553734575675767575568884556566475855685848485654864454663766645444574436774645376563234666326346443
566563433543322264347477663533766545634464344785486845767768576676857744758456485667758884677656583377736363347534654543534433463566366343363
555223422622655243643633767456657367445676386557685464545777868586864564484676684746564574488864774674453365474765677673543553322344356325443
666422265262655424456466666473554475447334585887857754757574584787868465865767476668456448656887677466674546647447665677555645354264545422234
563226422242366336753544557367656637776577466488685868775888744478784748675465587674767868556748745676644554534653566733733676636233445642336
322564234435646554674567377365335337747666488746766875574658858558556446886654658478845478476676888748467647663554665733455654534522662534653
465555623454633354445333653446736364557747546574447766445585886557886678584858674585768866455555764486685853766473443674575654742435232244663
343444333345462646773576447564676464457648776785566755578878787756544684757567485468846844788457564488844564553777663743437536532223424654325
262222464566654745464554475655357345664565788445885684557675677648778887486484857545754565467575775554645447446774764536337467454235536662643
232225445454333756373336674365336584675774545658567674845565785577665785455566754657474747566857554848688844854757347546577375635422363642242
426462234255434436537565533757765666754465558644788765657454865698895866888566895465865676454875485688586685856333457773757443455725433334645
536564545645475634464356564636775454456854468854545858586758597989866959966875956568758855675865676846478855774847754365447455345662662465465
635444422225455545664356536555546766677768765875554767747678579757857766887776587776987878886577846778548485657454356354566563375337625625244
354436534567735673766437774474565877786884768576467564566555758968956556889765687986686987865756455865744655777886676375663557576465533642236
564665643553557647746457345554877775644875885554756589687679868898765598699897996787695896548855684484468767648688664437743364557436753642366
562364622554366374664353374858757467476747844755657868879675897768996785676596568757988866759674578456455784488886586755755657734764436232336
264332654365666637556563657457756576848475886566996976778877778996886659858776775557879588599578845855748764454447585737365747667555744553465
534465655563445763544656646887457545478877655476988979997999978759788955558656988897978799577686578664666466758445658354357534445674363656354
442265464553344643664345447584444584678685788996976769556796788869989699698556766786866576777679974865845548854444757574344344733474574455225
462336673754537443367573555745685445476767587556988776979999959589587557999558699996957667867556799866545875787566646454665453464764454365364
335263637555343654737775467464784587484485585556778965787785896585755977777555689698897596999577598986548777644884557658454754554636344736262
234335766637333434546376845678668845775685795875967556579589797876866976986978887685859995675859857698744557566865874477576747466454533772422
255434574536534753637354455547567667765778595757897575599857866877978577859965585577889676598875996979764867485875854674453536534453655577222
434566643345555356464888454746767544687558976776679678677955866868767765969586776966879879685887568689876475854674445665645643347335464344356
534646336647757665335846455746868845678596765786877885787975659799696678879959758659766657987769879796977674644648784577553743545437435374322
526365737663437746666855544855754657787857895779598797959957869888886986987996999677785876678665985658777858668448457478565773676435774655566
265667734463653544354785567557576787658656969686597997765589868689979668997699966665695687879755957566977888847446885775864346753353374573535
253564543633573537474886666446566577786885575979777887666977886787987986687989689796888859686995995669797794674644768846685566646675743776375
244376776367766633545876687588456786855996899689566986669889969797878866997896967996696665557978668567558875577556657546684545554563757455776
554776573466745737474576745674745567776787959776557766566997867897986769676979869889676685769677969699775595547566885876544885443756344465663
257575556467766775454686547865888598556866678569556978678967688996698696799696998798787699896756867598989557556768454745464684763565434737545
537357564546643674458785745866754665595996755986665596688768796966787669977896868776776989968579766986785786678484777564864885657473634734343
565344664665535477747684777576746876656866585967989886866888699998877899979767668998996876979767669859877688885887574546786886546537664664373
565357774673666664574665685457558689795889587659668986987787779769889769786786677968688676789758795789778799968874554888745884477656333347734
245364636567733378747546688568467886556575995665667899776697867979969896777697699969798666967778955575878757679874445586566685865366343455347
575656654334567568656486467468659899798876975555697877868779698669996796698678666769878689967795566959879555869767654758764456537655557557767
346477444766645357588884555657666698776697587778967998678897767668969786678666998777877898879695965756995895677554566657887857845647373757563
664555364364376544585645485887676665565675956998886886898667766666879668669876889667796967869898765797966889859764865547768786566655366764647
663335573643645757784454578444798978988975897996797676789878998969987867899789769986867999888866857798899566596886878577678866667673443666553
665646477444467687777558754567958897787855565999966889777667798796689979878967869689697689969797678558687999957567777748468868754345565456346
566543636475566856656775656587756577667967799766766879688687889678977997888877768899789968667679679859556898886955486585464677474675534575777
645577757777546568576475846559988557689978768999899878797888686788977998778999799668866998997767768595597566666695577675758886657334537474335
647443537674646775664646644485579879756769756799977696899668878789789997979999998676969697669787776678878565876897478757886554676544436373733
735435337737668684557486784787968675575789587868997868887678797878989898977877897779967796786998868557559568875998648447577777687677333766745
543365534657558846755485555769955989956966898986769788686688788779788887978788778979999776788888866879568986868576657577867745756657476634333
575536335353367864458746645779595756876859568788987698977689998898877788798987888787886766966799886679868555575596986655665884467344356374634
473743773666654456848656885888576959596756697769979988779698977879787779899997998997896679869976797956886957756797747546478877674557735477576
645375747353758646565577776469995878658675789787886696789697888878888779887978789889769798679989886788698567658597588456647457688467657554557
345467535536675474848846568657895799758598699988889898977697988798798789797789877898877968986996666757886787886969865748864884847444663434663
656456334766548844754566855865579785857878878769986899686879798779888888997888797898876768676868879999656856958868968558486468757444637647463
464343374457778676587755854879865876988558978768686966967978999997987897797897799788898988987869996895799965888998677645657757588743463334546
347476457754374656475466676555567667657587886679767677688789978887987778988799997779879669999977768767865586875857875547687554665463564573454
453766454355684874884885874686876989695967697979669789668987897877898978887777778979796779986768878976856765759976868744885877575746735565357
736636647435668778784654646498787999669755687687679986876999779979898978899977999898789768998797877699878975986897764765448684554875364476735
664436647443567755668485684766596755555769978796767678869978778798988789998777777787997666686699786798677785879868965874785748455564663637575
433553345755375866788885748475965768586787978989798989696789999888799989878797978798798968789786967779856877995576767745856455666836337554377
344765347543374446674554858577596665697799687787679778869887879977999987999887979878796886977978987769865666868568956585866764566535774537475
546576646364778657445448847759585995895697878889778996669898789879989987799998979898797868677699766858578859977755677446755745878665767345653
533546474574554677555477646465886687856557896666778797998699899977899878877779778779867866897987667857887599895995588754757778486775455634365
364776533553388544476648645496597697688656897776688987669777788789989798888777777798988866877996776958558977857698778487778775567443437764654
767575643445774646865587678859868695688785899996688688877668879779779878879789879897668976796797988686797559759759646754568666464766356634777
663564774636658444884475474759797966777788768776999686687989799887988789889998777878788897969767689958777798865786678765766587576735546445447
765545346777444457678486575588879885678987596687678987878666897997977897979987978988767978769779979865598988867978478475444464744564356435353
366746667447578457875445867488677995859667698887779896696998788978887788989797887876769887968897796987657789656777858786758778587445346364346
734757577657577844678557878567659668878757786878767979787666669879779997977898778999886989869968789676788565887969468567446757675547746434465
467334563557566456758584574878865795766868658996987868887697669888997898899788998889989668879666986669776669687989566454585878855556675374743
645575457653677884784585588855655968856577875887769876987669779888778799897898777698889967796888787578585855865768848684455877667364474457775
767557477466374868477886488774898767588796985976996797898896789868898899977876979969877766999996989576756859996757575867468868557576573774434
365367356554353486664888444486576978789969667598668798779679967888788999796986688989987679989688677766569979655954458755548884553647454343365
376336736735457876455766664576868899958567899859897696666876898967968667669679868898898888678777677965768667886556674567766854753575675577476
655377576336353777555487674664459995998755596688788868897878878786779897766898666796798699986769596797666758675744757446578744875557637667343
346446435544365588467868786546676559596578965787878788879688679686797787696768968886787989768785998568785579588888765488767877567565467755576
354754743465663748676677684474685586888867755998899878766698966778769666867868877666879989869975667775996755968584457547448868665676574646644
375476567446766648657685558868684876569896777896588689767787787777779797666866966896997697886777658855887666756556865488575868637476356664546
445443376634364754578848556856444996665555889556557986866898987898998767968769789997987768997597899598677768594578757748767547673755546757466
665475644545575348685574648545765657959867595696876978696669997879986966979668799877788966668889557878656677776786455675445767467546444535474
536536364733663343757854644865786455596579777665886777767776796878787689898768677668688795585588869858867558758654576484588863577736365556466
545677765673477647458587675877857747699998588967985579966698996796669968868886777876896876566779758656867579564454754855855877653657775474465
526634533344674357784857678766684666995887697768597868868688669877886679676996996687797775768787576675996687784778756557686657567343466435376
555367765673445476467455475554586466585989789887787769676867966767676796687889896986877586778976986876898895566876577547785676354466367535475
566676343464545754336756566678644764665555658957956858897698698967768969799997687799675666769956667655559976654874668868864344365374536646744
642375475753557633436874464648878466547566967655869789865959766986877898877867796965686987965766886865865675747548555887646747776445567347646
656326775677733743553476855846684858777567795889655999758996557887666699887977775858955696758766587856867888675575847875564373546374366533364
356523464767556365754554458685647747687488976778688855697796599685596579789897557585667697756877865679768565567847486476653374377755437773466
543364557655446374776484667446844587777758978869866755687997557969558968989668567678676658666557568857756646588867747655633365453645345346563
236562656367457666473574756767787484864787678758988675958855996858589889785858687986999988859888998997488777755668648846466573577345536445525
435425454743354543343534475784886747857444675996758965666578678996855698756785979795587987959775967867864775685466445885737645534737473665362
656365663566663445676743748865778774886455467789977566999699575957678987978899885895585598567758556556745674586867685465366373764453753632226
554364645654577774575347585474486665445484788787958557777995767555969688786699755588897576959596976845578586878455558754775543573553676466226
566365526354555656773564765857585674685586764446576595576665977697577778959689988577969857867777544786674878657577858777336353333336763243544
225645463477536636737547746855854577665455586777855595668788968669666569588785557968878679887868765668784484567586587654537447376767635645624
326343324673543334344333453846654874888454446758467889966666595596659955785659698886979596579556454785744657484756587664635335666734746333362
532662633633547457656367653444766558747845867568768765978675586896665555887897795567797775544675848675458648484474634746576546564554542654353
355663354646374655677455353646574544555776878645666884896787558788857879795677987878598875568878457856645555765646757774773335733663526234223
353422562247634437354366757547848484486845777858677644677756767685987785766977575755599856685775568757588558668567757543337544345564535234266
625553254333746337646674767563388458857564687664846777856669755559789686587569959585684667544648664446655584855854567365533744356742364465444
256524322524363455666676457677636858464476685768488658555885585999765659786578666675884764747557458554788587577463354747475464475463564363232
344555253446556735453434354367637586487674456777465645884457744886765674748655466874854454886874745687874444873743475747434554764722562353544
436336633646457553373364653633435565546884675847685764745576446566586448474646588477788544776856755887755886845455353675573457356665354253225
353553554345353455733547735663756547845588454848874587864766784664557578755786484855447586484587747576577446434565477633534576642362554466224
432525456624322674674455473444735465585878467468565785857768745885767848488547466474785564885557558774875737646763773465674537654223644552654
525335354433465274655555537746447754355487677744768868776677444557756865777755446886557446678584767648468645477543475677473764432555343662443
536234524632522465555647777335435334437785748846755474465446555657555454476786768444746644457754678455575643465746465774734443646245244645242
543442426643426534477636563376653536756355858585748486864457846887545584748846488758855855645876464887457465374457355477665635626433523524452
223322223546552553575645377567767764633457777574576586688766475584868555884876446564687754664544674746647356433575667577763565225654256544622
125432653256262246645676433475543465775457456787477566566648476474677745847886586875848787748885486346376633653653363657636242326523563666434
154555463335463666563736355477665434373773447735676677764476767476757886646475666486685555778786577733434376677574533676446342454463463634432
141552262546462536364674453376344346655766473635575565475486864645767844585465884467586667565773377733634663557773445746422526356353452324542
312423654364225622226637376343347535467656737454465678885885746745857776864757467665478865575446666474647437757675757473645242266443443325554
333352266326435462625366644556555677753333564555775666584874665848744466545484587654854464745467733645434647766364433755226524223666554626514
435132545534652226544462427766367457556547533646553733455368768864748656858757658764667566573447736343373755745347737256566566356246552554344
251251242554456622643453332655755467667663776573476475365556464548586464744786567334573766376654353443634574576453465245553624544653336543111
212442344546526645642263244654774376666364765664337477476566755735634734545547537453654634467644564673444576465347666352444336246443534225131
112553156446434342262332632662776733455533536546447357345533465336456677743746473675453643333635675467467446533763524242322555366262662253531
211154334644242354452264624333677734447567476373463347474347444453644577737565635654763766744377535655635747756455462332222243526345542432111
452531315135444354222633542256663373756457456776563646334754543544575364335767774564575736767736775545744343363363624653264666332236225512123
554211544546426525425562633634342635553437466647567764434744664546375647473767773675456535466347457734537637645252643554463622523335443333224
334533452455542655362226365236322545337345466373753756677574663767643737437554464546345477754476745457537446262223644636236336656625515513231
452555231215326224366256565643522266556465346746347363633645746436473667767556763464673664753345776465737364364536446645553352366221223144345
514335112142516342564642545262662364262353574573475464554553456636477477446756645474374646364357353537766264336222226532264353454144251545325
152522253244513266563264433552644226246665674554677745755364563737344773646764375565657457543353753423534335226422232656264234264153315553535
324514541241141455232546254624542356544332452737546335476443477344545643434547765335573737455674436465526432346264244552654644651313224214233
213141543243524321434324633656252333252323653563475667336736466576733354556565346365373663374333256546644423653255346636444624514124522425212

13
day17/sample1.in 100644
View File

@ -0,0 +1,13 @@
2413432311323
3215453535623
3255245654254
3446585845452
4546657867536
1438598798454
4457876987766
3637877979653
4654967986887
4564679986453
1224686865563
2546548887735
4322674655533

58
day17/sol.py 100644
View File

@ -0,0 +1,58 @@
import astar
def read_input(f):
map = []
for line in f:
map.append([int(x) for x in line.strip()])
return map
def solve(map,part=1):
start = (0,0,(0,0),0)
goal = (len(map)-1,len(map[-1])-1)
def is_goal(x):
return x[:2] == goal
def neighbors(state):
y,x,dir,count = state
next = []
def go(dx,dy):
if (-dx,-dy) == dir:
# can't turn around
return
newx = x + dx
newy = y + dy
if (dx,dy) == dir:
newcount = count+1
else:
newcount = 1
if part == 1:
if newcount > 3:
return
if part == 2:
if newcount > 10:
return
if newcount <= count < 4:
return
if (0 <= newy < len(map)) and (0 <= newx < len(map[newy])):
next.append((map[newy][newx], (newy, newx, (dx,dy), newcount)))
go(-1,0)
go(+1,0)
go(0,-1)
go(0,+1)
return next
cost, node, path = astar.search(start, is_goal, neighbors)
print(cost)
print([(x,y) for (y,x,_,_) in path])
print(''.join(dir2s(d) for (_,_,d,_) in path))
def dir2s(d):
if d == (0,1): return "v"
if d == (0,-1): return "^"
if d == (1,0): return ">"
if d == (-1,0): return "<"
return "?"
import sys
map = read_input(sys.stdin)
solve(map, part=1)
solve(map, part=2)

618
day18/input 100644
View File

@ -0,0 +1,618 @@
L 7 (#357ea0)
U 2 (#931393)
L 4 (#3a7350)
U 10 (#02c563)
L 4 (#81f110)
U 5 (#74d543)
L 9 (#256002)
U 6 (#708cf3)
L 4 (#4c90e0)
U 8 (#0ac253)
L 8 (#4c90e2)
U 5 (#693483)
R 6 (#256000)
U 6 (#27cc33)
R 8 (#3bf170)
U 3 (#376663)
L 4 (#035da0)
U 6 (#045753)
L 10 (#826390)
U 4 (#7a8c43)
L 10 (#271b30)
U 10 (#6d21f3)
L 10 (#4a97c2)
D 2 (#641f33)
L 6 (#8468c2)
D 3 (#4316e3)
R 10 (#2dc6b2)
D 11 (#5776a3)
R 7 (#6319d0)
D 7 (#6573e3)
L 11 (#7e0de0)
D 6 (#7d1f63)
L 6 (#4c51e2)
D 5 (#5de033)
L 5 (#59cb30)
U 11 (#2bb943)
L 3 (#434650)
U 6 (#2bb941)
L 8 (#20d440)
U 6 (#3c4843)
L 4 (#535852)
D 6 (#818223)
L 7 (#144d02)
U 4 (#818221)
L 3 (#564072)
U 5 (#2e7f43)
L 12 (#4c51e0)
U 9 (#3b61d3)
L 9 (#14d352)
U 4 (#727ac3)
L 7 (#2f39c2)
U 7 (#0516d3)
L 4 (#9d1aa2)
U 4 (#22d7e3)
R 9 (#321810)
U 6 (#740ad3)
R 5 (#4cfb40)
D 7 (#740ad1)
R 8 (#38f8c0)
D 11 (#1f22e3)
R 4 (#0e5630)
U 18 (#62bcb3)
R 3 (#292920)
D 6 (#7b6263)
R 3 (#0d3bd0)
U 9 (#82c2b3)
L 8 (#426530)
U 13 (#40cf11)
L 2 (#2ca6c0)
U 4 (#577ac1)
L 6 (#1ec6a0)
U 3 (#247691)
L 10 (#69b330)
U 6 (#3db1f3)
L 5 (#357750)
U 5 (#adbae3)
L 13 (#508510)
D 8 (#0ebc21)
L 2 (#11ae92)
D 4 (#8e3c61)
L 12 (#11ae90)
U 9 (#4e7451)
L 8 (#11ac20)
U 3 (#633511)
L 3 (#1091b2)
U 16 (#5b17e1)
R 3 (#25f402)
U 4 (#50ed21)
R 13 (#50e172)
U 8 (#ac0503)
R 13 (#5ca752)
U 9 (#119051)
R 4 (#012c32)
U 8 (#aabdf1)
R 2 (#678e72)
U 5 (#46f071)
R 7 (#890120)
U 4 (#0c2131)
R 7 (#62ffe0)
U 10 (#08cdc1)
R 7 (#0927c0)
D 14 (#880c31)
R 7 (#0927c2)
U 9 (#4043a1)
R 3 (#533660)
U 4 (#314eb3)
R 5 (#89f670)
D 7 (#59a0f3)
R 11 (#41cfc0)
D 9 (#20c953)
L 8 (#83fc42)
D 9 (#798a53)
L 2 (#83fc40)
D 11 (#2f7c73)
R 10 (#5a7880)
D 4 (#72f003)
R 4 (#184650)
D 3 (#1146d1)
R 5 (#5ce420)
D 4 (#915c31)
R 11 (#257a20)
U 5 (#78faf3)
R 13 (#595510)
U 8 (#29a813)
R 3 (#050b70)
U 8 (#1bcac3)
R 12 (#53c3a0)
U 3 (#752613)
R 10 (#282602)
U 7 (#6d5a53)
R 6 (#6266d2)
U 6 (#0ff141)
R 8 (#40f1e2)
U 6 (#0ff143)
R 7 (#814a02)
U 9 (#22a8b3)
R 2 (#469720)
U 2 (#358e33)
R 12 (#9d5ce0)
D 5 (#358e31)
R 3 (#2cb960)
D 3 (#17cf63)
L 4 (#a20580)
D 4 (#29c2e1)
L 10 (#9c87f0)
D 5 (#3cd241)
R 8 (#4c6400)
D 2 (#3aca21)
R 2 (#661a10)
D 9 (#997e51)
L 3 (#661a12)
D 4 (#4c65e1)
L 7 (#82e570)
D 4 (#72e2a1)
R 14 (#369ab0)
D 3 (#256c01)
R 7 (#7449e0)
D 7 (#582f41)
R 8 (#820b42)
U 5 (#212c51)
R 7 (#30a812)
U 6 (#8bd2f1)
L 5 (#8e4622)
U 12 (#016441)
L 6 (#030532)
U 9 (#7ffcc1)
L 4 (#362f62)
U 4 (#41b291)
R 10 (#77ccb0)
U 7 (#3e3811)
R 5 (#52abd0)
U 3 (#3e3813)
R 13 (#30e6c0)
U 6 (#2763d3)
R 13 (#468d70)
U 9 (#2763d1)
R 4 (#490740)
U 5 (#16c7b1)
R 13 (#0698c0)
U 3 (#3092a1)
L 6 (#34dc72)
U 5 (#6eedb1)
L 4 (#34dc70)
U 5 (#3bb131)
L 13 (#60d040)
U 3 (#502ad1)
L 3 (#42e190)
U 16 (#1550a1)
L 5 (#9144e0)
U 5 (#0e1761)
L 9 (#0740d2)
U 7 (#4ff951)
L 8 (#2ca952)
U 7 (#309051)
L 3 (#a03c52)
U 12 (#05c2d1)
L 3 (#800432)
U 8 (#3dce71)
L 5 (#192882)
U 9 (#4c2d43)
L 5 (#419c22)
U 5 (#b1aaf3)
L 4 (#66bec2)
U 6 (#24f6a3)
L 7 (#2d7eb2)
U 10 (#5c6651)
L 6 (#167982)
D 6 (#5e9201)
L 7 (#167980)
D 10 (#1ba941)
L 6 (#1887a2)
D 4 (#4c2d41)
R 12 (#465332)
D 7 (#4f4261)
L 5 (#18f3b2)
D 14 (#3a0001)
R 5 (#18f3b0)
D 5 (#477441)
R 11 (#03f1b0)
D 7 (#66e581)
L 6 (#09d890)
D 8 (#3db093)
L 9 (#252580)
D 7 (#1b8853)
L 3 (#963ea0)
D 6 (#1b8851)
L 5 (#132d70)
D 8 (#3db091)
L 8 (#0f6be0)
D 6 (#66e583)
L 5 (#5e59d0)
U 10 (#1fe881)
R 4 (#4b8912)
U 10 (#7eb3c1)
L 7 (#4b8910)
D 8 (#166151)
L 7 (#49db70)
U 8 (#02a761)
L 10 (#39e420)
U 3 (#492dd1)
R 6 (#48e850)
U 5 (#703fb1)
R 16 (#4c6b72)
U 3 (#10fdd1)
R 2 (#359bc2)
U 3 (#a2b691)
L 4 (#3c6712)
U 3 (#0613b1)
L 11 (#53dde2)
U 11 (#662e11)
L 10 (#7164d2)
U 3 (#3af111)
R 4 (#3a2be2)
U 3 (#040021)
R 3 (#0da842)
U 3 (#b32a51)
R 4 (#52af42)
U 15 (#035bb1)
R 6 (#0d6b52)
U 5 (#261bd1)
R 5 (#7314e0)
U 3 (#50ed33)
L 13 (#526630)
U 5 (#704043)
L 9 (#3f1350)
U 7 (#0c7273)
R 5 (#493b90)
U 2 (#30c193)
R 9 (#33ba10)
U 7 (#75b9c3)
R 7 (#0c2ef0)
U 8 (#042593)
R 10 (#5b3cc0)
U 10 (#66b891)
R 8 (#33d8e0)
U 5 (#43e851)
R 3 (#30ca70)
U 2 (#099de1)
R 8 (#54ef50)
U 5 (#4adfa1)
R 5 (#87a9b2)
U 6 (#765601)
R 2 (#87a9b0)
U 8 (#02cc61)
L 14 (#063ef0)
U 6 (#242451)
R 5 (#04c3f0)
U 3 (#2622d1)
R 11 (#770830)
U 9 (#64cd61)
R 8 (#3f7700)
U 3 (#97bc41)
L 14 (#4328a0)
U 6 (#1d3ed1)
L 10 (#3f5090)
U 10 (#549f11)
R 5 (#401c12)
U 9 (#1db141)
R 9 (#3ab0c2)
U 6 (#027201)
R 12 (#8398b2)
U 2 (#5e76d1)
R 6 (#6b9210)
D 6 (#59c901)
R 9 (#6b9212)
D 5 (#23be31)
R 5 (#170352)
D 6 (#6404d1)
R 12 (#4577e0)
D 7 (#a84041)
L 14 (#4a3910)
D 4 (#528a21)
L 4 (#459bd0)
D 8 (#5c3d21)
L 4 (#6efdb2)
D 6 (#20a931)
R 3 (#15cd22)
D 7 (#7c9c13)
R 6 (#7e8af2)
D 6 (#2b0663)
R 7 (#304942)
D 3 (#277bb3)
R 6 (#2ade02)
D 3 (#b2ff33)
R 13 (#2524b2)
D 3 (#1cc843)
R 4 (#6c16c2)
D 3 (#876163)
R 3 (#436032)
D 8 (#6520e1)
R 2 (#1c69d2)
D 15 (#a123d1)
R 5 (#1c69d0)
U 6 (#785fd1)
R 3 (#18e722)
D 11 (#a7a271)
R 7 (#04d402)
D 3 (#20a933)
R 10 (#83d842)
D 5 (#89d7b1)
R 4 (#672c02)
D 10 (#394b21)
R 5 (#520a32)
D 4 (#5b1951)
R 8 (#187f52)
D 3 (#471901)
R 7 (#2d9542)
D 13 (#b049b1)
R 3 (#526ba2)
D 9 (#6445d3)
R 5 (#7ddda2)
D 2 (#6445d1)
R 17 (#8f7f92)
D 3 (#824f13)
R 9 (#29ec62)
D 4 (#31cb73)
R 8 (#53c0a2)
D 7 (#1b1321)
L 6 (#6183d2)
D 3 (#4e9f01)
L 3 (#6582e2)
D 13 (#484c11)
R 9 (#0683e0)
D 8 (#8186e1)
L 7 (#7c7340)
D 7 (#8186e3)
L 4 (#440f90)
D 8 (#1ba571)
L 7 (#267130)
D 6 (#288601)
L 3 (#6c3dc0)
U 8 (#36ceb1)
L 2 (#03b370)
U 10 (#27e7d1)
L 3 (#4ecfd0)
U 6 (#840633)
L 6 (#281d50)
U 4 (#840631)
L 8 (#70c000)
D 11 (#27e7d3)
L 8 (#506fe0)
D 2 (#36ceb3)
L 7 (#549e70)
D 4 (#3855e1)
R 7 (#826de2)
D 4 (#459461)
R 8 (#1b5db2)
D 7 (#588f91)
L 8 (#97c742)
D 4 (#72fbf1)
L 5 (#5ea652)
D 5 (#565203)
L 13 (#4d0d22)
D 9 (#753983)
R 13 (#40f5b2)
D 5 (#459463)
L 4 (#00e1e2)
D 3 (#054db1)
R 7 (#1109b2)
D 3 (#51ac81)
R 6 (#786302)
D 5 (#1d4111)
R 11 (#384d62)
D 8 (#0abf31)
R 3 (#9e4960)
D 2 (#56d781)
R 5 (#2370b0)
U 15 (#1e2401)
R 5 (#015242)
D 2 (#09c081)
R 10 (#068442)
D 6 (#8b50f1)
R 2 (#74fa32)
D 6 (#8b50f3)
R 3 (#5c62e2)
D 9 (#4e15b1)
R 9 (#882932)
D 11 (#5207a3)
R 6 (#858b62)
D 6 (#87cd73)
R 4 (#389ac2)
D 8 (#0093b3)
R 6 (#2c2582)
D 6 (#483b71)
R 4 (#967a82)
D 11 (#483b73)
R 8 (#139412)
D 3 (#43d833)
R 3 (#39ce82)
D 12 (#1b3e53)
R 10 (#70ef10)
D 4 (#2cb373)
L 13 (#32fb60)
D 3 (#5239e3)
L 13 (#98c7d2)
D 4 (#323a43)
L 13 (#0b22a2)
D 8 (#2ce053)
L 7 (#7696e2)
D 7 (#505353)
L 8 (#b06560)
D 11 (#127133)
R 3 (#0a2af2)
D 10 (#7fcd23)
R 11 (#646af2)
D 9 (#19db13)
R 3 (#1facf2)
D 4 (#278353)
R 9 (#7da710)
D 12 (#97eec3)
R 3 (#324190)
D 7 (#0d7793)
R 4 (#afe8a2)
D 10 (#5c84d3)
R 5 (#812562)
D 4 (#2d50f3)
L 16 (#b1f652)
D 3 (#051f51)
L 6 (#47f1c2)
D 10 (#9968d1)
L 2 (#64a0a2)
D 6 (#9968d3)
L 6 (#6b9ae2)
D 2 (#6972b3)
L 8 (#319422)
D 6 (#a5c243)
L 6 (#1572e0)
D 5 (#a2e233)
R 13 (#1572e2)
D 8 (#0f0be3)
R 7 (#5c79c2)
D 3 (#2ebab1)
R 3 (#431082)
D 10 (#090461)
R 5 (#222c82)
D 9 (#4e4681)
L 4 (#732d30)
U 6 (#678f01)
L 5 (#387c20)
U 9 (#71c291)
L 7 (#aba952)
D 11 (#059f41)
L 4 (#222c80)
D 4 (#3944a1)
L 8 (#431080)
D 7 (#22e801)
R 6 (#03da22)
D 4 (#264601)
L 6 (#5eb852)
D 7 (#2cb323)
L 13 (#1d2bd2)
D 2 (#2cb321)
L 3 (#5b2ef2)
U 9 (#264603)
L 2 (#16f302)
U 6 (#051f53)
L 9 (#4bd602)
U 4 (#385d93)
L 9 (#736600)
U 6 (#38ebf3)
L 13 (#41dc90)
U 5 (#073e13)
L 6 (#031ff0)
U 11 (#784b53)
L 5 (#50b290)
U 7 (#3e8d53)
L 8 (#50b292)
U 5 (#752f43)
L 15 (#4583e0)
U 5 (#7dbe13)
L 3 (#8db280)
U 4 (#4212a1)
L 12 (#a4bbf0)
U 3 (#66d011)
L 5 (#336120)
U 4 (#479a81)
R 6 (#78af90)
U 4 (#352181)
R 5 (#78af92)
U 10 (#421b01)
R 5 (#4143e0)
U 4 (#494a51)
R 13 (#57dea0)
U 9 (#312a23)
R 12 (#894440)
U 6 (#312a21)
R 5 (#4e2a70)
U 4 (#61a223)
R 3 (#1c5820)
U 7 (#146ba1)
R 5 (#4da250)
U 3 (#146ba3)
R 10 (#555d30)
U 2 (#52e6c3)
R 3 (#078620)
U 12 (#23ce33)
L 10 (#15b752)
U 5 (#3447b1)
L 8 (#656962)
U 9 (#3447b3)
L 3 (#65f2b2)
D 14 (#05c0d3)
L 4 (#20fb32)
U 10 (#23fea3)
L 11 (#6fb332)
U 9 (#3eac33)
L 7 (#00ea52)
D 13 (#8b56d3)
L 2 (#115f30)
D 7 (#365993)
L 2 (#167ef0)
D 3 (#3a33e3)
L 2 (#1e9ef0)
D 7 (#755883)
L 5 (#6e64b0)
D 5 (#6b9661)
L 6 (#76e2b0)
U 3 (#43f601)
L 5 (#46e7a0)
U 7 (#5c9be3)
L 3 (#328892)
U 9 (#8c7073)
R 5 (#3c6020)
U 6 (#943bd3)
R 3 (#498750)
U 10 (#0f8f33)
L 11 (#36f0f0)
D 7 (#2af483)
L 12 (#207430)
D 3 (#0c9011)
L 10 (#0ed572)
D 5 (#426c31)
L 9 (#7ddd92)
D 5 (#319fb1)
R 11 (#7ddd90)
D 4 (#44de41)
R 6 (#0ed570)
D 3 (#094551)
R 10 (#004c10)
D 4 (#6b53f3)
L 11 (#506b90)
D 4 (#2f2a23)
L 5 (#39b5f0)
D 3 (#8ca543)
L 6 (#39b5f2)
D 10 (#20ea63)
L 2 (#66cec0)
D 2 (#22cf93)
L 11 (#3ee352)
D 6 (#591893)
R 12 (#14d660)
D 4 (#5c95f3)
R 3 (#14d662)
D 4 (#37d7b3)
R 5 (#025f32)
D 13 (#7ddd23)
L 8 (#3a93c2)
D 4 (#063123)
L 12 (#9a7522)
D 3 (#61ae11)
R 9 (#572b22)
D 4 (#4fcde1)
R 9 (#130512)
U 4 (#a1ee51)
R 6 (#130510)
D 4 (#1e2a31)
R 11 (#275c72)
D 3 (#129543)
L 10 (#585302)
D 11 (#608d93)
L 8 (#62bf02)
U 11 (#27f113)
L 9 (#322732)
D 3 (#4a7f63)
L 6 (#664bb2)
U 6 (#5a4ea3)
L 9 (#507222)
U 3 (#2e1ca3)

14
day18/sample1.in 100644
View File

@ -0,0 +1,14 @@
R 6 (#70c710)
D 5 (#0dc571)
L 2 (#5713f0)
D 2 (#d2c081)
R 2 (#59c680)
D 2 (#411b91)
L 5 (#8ceee2)
U 2 (#caa173)
L 1 (#1b58a2)
U 2 (#caa171)
R 2 (#7807d2)
U 3 (#a77fa3)
L 2 (#015232)
U 2 (#7a21e3)

57
day18/sol.tcl 100755
View File

@ -0,0 +1,57 @@
#!/usr/bin/env tclsh
proc solve {input} {
set data {}
while {[gets $input line] >= 0} {
lappend data $line
}
set data [join $data]
set x 0
set y 0
set y0 0
set y1 1
set x0 0
set x1 1
set grid [dict create 0,0 1]
foreach {dir steps color} $data {
puts "$x $y $dir $steps $color"
for {set i 0} {$i < $steps} {incr i} {
switch $dir {
{U} {incr y -1}
{D} {incr y}
{L} {incr x -1}
{R} {incr x}
}
dict set grid $x,$y 1
set x0 [expr {min($x0,$x)}]
set y0 [expr {min($y0,$y)}]
set x1 [expr {max($x1,$x+1)}]
set y1 [expr {max($y1,$y+1)}]
}
}
set t 0
for {set y $y0} {$y < $y1} {incr y} {
set row ""
set in 0
for {set x $x0} {$x < $x1} {incr x} {
if {[dict exists $grid $x,$y]} {
if {[dict exists $grid $x,[expr {$y+1}]]} {
set in [expr {!$in}]
}
lappend row "#"
incr t
} else {
if {$in} {
lappend row "o"
incr t
} else {
lappend row "."
}
}
}
puts [join $row ""]
}
puts "$t"
}
solve stdin

81
day18/sol2.tcl 100755
View File

@ -0,0 +1,81 @@
#!/usr/bin/env tclsh
proc solve {input} {
set data {}
while {[gets $input line] >= 0} {
set color [string trim [lindex $line 2] "()"]
set dir [lindex {R D L U} [string index $color end]]
set steps [scan [string range $color 1 end-1] "%x"]
lappend data $dir $steps $color
}
puts $data
set x 0
set y 0
set extra 0
set yrays {}
foreach {dir steps color} $data {
puts "$x $y $dir $steps $color"
set oldy $y
set oldx $x
switch $dir {
{U} {incr y -$steps}
{D} {incr y +$steps}
{L} {incr x -$steps}
{R} {incr x +$steps}
}
if {$oldy < $y} {
lappend yrays [list $oldy $y $x]
} elseif {$y < $oldy} {
lappend yrays [list $y $oldy $x]
}
if {$oldy != $y} {
incr extra [expr {abs($oldy - $y)}]
}
if {$oldx != $x} {
incr extra [expr {abs($oldx - $x)}]
}
}
#puts $yrays
set ypos {}
foreach {a b x} [join $yrays] {
lappend ypos $a $b
}
set ypos [lsort -integer -unique $ypos]
set t 0
puts $ypos
foreach y $ypos yn [difference $ypos] {
if {$yn eq ""} {
continue
}
set xpos {}
foreach {a b x} [join $yrays] {
if {$a <= $y && $y < $b} {
lappend xpos $x
}
}
set xpos [lsort -integer $xpos]
puts "$y +$yn : $xpos"
if {[llength $xpos] == 0} { error "no xpos" }
set in 0
foreach x $xpos xn [difference $xpos] {
set in [expr {!$in}]
if {$in && $xn ne {}} {
incr t [expr {($xn) * ($yn)}]
}
}
}
#puts "$t"
# +1 for the outer perimeter, -1 for the inner perimeter
incr t [expr {$extra/2 + 1}]
puts "$t"
}
proc difference lst {
set out {}
for {set i 1} {$i < [llength $lst]} {incr i} {
lappend out [expr {[lindex $lst $i] - [lindex $lst $i-1]}]
}
return $out
}
solve stdin

View File

@ -4,11 +4,15 @@ namespace import tcl::mathfunc::max
proc {#} args {}
# short aliases for common things
proc llen {lst} { return [llength $lst] }
proc slen {str} { return [string length $str] }
proc trim args { return [uplevel [concat string trim $args]] }
proc replace {str a b} { return [string map [list $a $b] $str] }
# sum and product
proc ladd {list} {
set t 0
foreach x $list { incr t $x }
@ -33,7 +37,13 @@ proc must_regexp args {
}
}
# transpose an array of strings
# transpose a list of strings
#
# % transpose {abc 123}
# a1 b2 c3
# % transpose a1 b2 c3
# abc 123
#
proc transpose strings {
set out {}
set C [slen [lindex $strings 0]]
@ -46,3 +56,45 @@ proc transpose strings {
}
return $out
}
# transpose a list of lists
#
# % ltranspose {{a b c} {1 2 3}}
# {a 1} {b 2} {c 3}
# % ltranspose {{a 1} {b 2} {c 3}}
# {a b c} {1 2 3}
#
proc ltranspose lists {
set out {}
set C [llen [lindex $lists 0]]
for {set i 0} {$i < $C} {incr i} {
set column {}
foreach row $lists {
lappend column [lindex $row $i]
}
lappend out $column
}
return $out
}
# extracts one or more indexes from a strided list
# e.g.
# % set l {0 1 2 a b c x y z}
# % lextract $l 3 0
# 0 a x
# % lextract $l 3 {1 2}
# 1 2 b c y z
#
# equivalent to [lmap {a b c} $lst {list $b $c}] except that
# you don't have to name the list elements
proc lextract {lst stride index} {
set i 0
set out {}
if {$stride <= 0} { error "stride must be positive: $stride" }
for {set i 0} {$i < [llength $lst]} {incr i $stride} {
foreach j $index {
lappend out [lindex $lst $i+$j]
}
}
return $out
}