question 9A
This commit is contained in:
1 parent
8198014f66
commit
6e61950ee2
4 files changed
+496
No files matched your search
@@ -0,0 +1,263 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
type DllId int64
|
||||||
|
|
||||||
|
type DoubleLinkedList[T any] struct {
|
||||||
|
data map[DllId]T
|
||||||
|
nodes map[DllId]*DLLNode
|
||||||
|
FirstNode DllId
|
||||||
|
LastNode DllId
|
||||||
|
length int
|
||||||
|
lastGeneratedId DllId
|
||||||
|
}
|
||||||
|
|
||||||
|
func NewDLL[T any]() *DoubleLinkedList[T] {
|
||||||
|
return &DoubleLinkedList[T]{
|
||||||
|
make(map[DllId]T),
|
||||||
|
make(map[DllId]*DLLNode),
|
||||||
|
-1,
|
||||||
|
-1,
|
||||||
|
0,
|
||||||
|
-1,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
type DLLNode struct {
|
||||||
|
Id DllId
|
||||||
|
NextId DllId
|
||||||
|
PreviousId DllId
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) IsEmpty() bool {
|
||||||
|
return l.length == 0
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) insertEmpty(data T) DllId {
|
||||||
|
newId := l.nextId()
|
||||||
|
node := standaloneNode(newId)
|
||||||
|
l.data[newId] = data
|
||||||
|
l.nodes[newId] = node
|
||||||
|
l.FirstNode = newId
|
||||||
|
l.LastNode = newId
|
||||||
|
l.length++
|
||||||
|
return newId
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) InsertBefore(id DllId, data T) (DllId, bool) {
|
||||||
|
if node, ok := l.nodes[id]; ok {
|
||||||
|
return l.insertBetween(l.previousNode(node), node, data)
|
||||||
|
} else {
|
||||||
|
return -1, false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) InsertAfter(id DllId, data T) (DllId, bool) {
|
||||||
|
|
||||||
|
if node := l.nodes[id]; node.Id == id {
|
||||||
|
return l.insertBetween(node, l.nextNode(node), data)
|
||||||
|
}
|
||||||
|
|
||||||
|
return -1, false
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) InsertFirst(data T) DllId {
|
||||||
|
if l.IsEmpty() {
|
||||||
|
return l.insertEmpty(data)
|
||||||
|
}
|
||||||
|
newId := l.nextId()
|
||||||
|
node := standaloneNode(newId)
|
||||||
|
l.data[newId] = data
|
||||||
|
l.nodes[newId] = node
|
||||||
|
firstNode := l.nodes[l.FirstNode]
|
||||||
|
node.NextId = firstNode.Id
|
||||||
|
firstNode.PreviousId = newId
|
||||||
|
l.FirstNode = newId
|
||||||
|
l.length++
|
||||||
|
return newId
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) InsertLast(data T) DllId {
|
||||||
|
if l.IsEmpty() {
|
||||||
|
return l.insertEmpty(data)
|
||||||
|
}
|
||||||
|
newId := l.nextId()
|
||||||
|
node := standaloneNode(newId)
|
||||||
|
l.data[newId] = data
|
||||||
|
l.nodes[newId] = node
|
||||||
|
lastNode := l.nodes[l.LastNode]
|
||||||
|
node.PreviousId = lastNode.Id
|
||||||
|
lastNode.NextId = newId
|
||||||
|
l.LastNode = newId
|
||||||
|
l.length++
|
||||||
|
return newId
|
||||||
|
}
|
||||||
|
|
||||||
|
func standaloneNode(id DllId) *DLLNode {
|
||||||
|
return &DLLNode{id, -1, -1}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) nextId() DllId {
|
||||||
|
l.lastGeneratedId++
|
||||||
|
return l.lastGeneratedId
|
||||||
|
}
|
||||||
|
|
||||||
|
func mapNodes[T, K any](l *DoubleLinkedList[T], fn func(T, *DLLNode) K) <-chan K {
|
||||||
|
ch := make(chan K)
|
||||||
|
go func() {
|
||||||
|
defer close(ch)
|
||||||
|
iterId := l.FirstNode
|
||||||
|
for iterId > -1 {
|
||||||
|
val := fn(l.data[iterId], l.nodes[iterId])
|
||||||
|
ch <- val
|
||||||
|
iterId = l.nodes[iterId].NextId
|
||||||
|
|
||||||
|
}
|
||||||
|
}()
|
||||||
|
return ch
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) Iter() <-chan T {
|
||||||
|
return mapNodes(l, func(datum T, node *DLLNode) T { return datum })
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) IterIds() <-chan DllId {
|
||||||
|
return mapNodes(l, func(datum T, node *DLLNode) DllId { return node.Id })
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) IterNodes() <-chan *DLLNode {
|
||||||
|
return mapNodes(l, func(datum T, node *DLLNode) *DLLNode { return node })
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) IterIdsFromLast() <-chan DllId {
|
||||||
|
ch := make(chan DllId)
|
||||||
|
go func() {
|
||||||
|
defer close(ch)
|
||||||
|
iterId := l.LastNode
|
||||||
|
for iterId > -1 {
|
||||||
|
ch <- iterId
|
||||||
|
iterId = l.nodes[iterId].PreviousId
|
||||||
|
}
|
||||||
|
}()
|
||||||
|
return ch
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) GetById(id DllId) (T, bool) {
|
||||||
|
if d, ok := l.data[id]; ok {
|
||||||
|
return d, ok
|
||||||
|
} else {
|
||||||
|
var empty T
|
||||||
|
return empty, false
|
||||||
|
}
|
||||||
|
//for iterId := range l.IterIds() {
|
||||||
|
// if iterId == id {
|
||||||
|
// return l.data[id], true
|
||||||
|
// }
|
||||||
|
//}
|
||||||
|
//var nilValue T
|
||||||
|
//return nilValue, false
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) Last() (T, bool) {
|
||||||
|
if l.IsEmpty() {
|
||||||
|
var empty T
|
||||||
|
return empty, false
|
||||||
|
}
|
||||||
|
return l.data[l.lastGeneratedId], true
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) LastId() (DllId, bool) {
|
||||||
|
if l.IsEmpty() {
|
||||||
|
return -1, false
|
||||||
|
}
|
||||||
|
return l.LastNode, true
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) FirstId() (DllId, bool) {
|
||||||
|
if l.IsEmpty() {
|
||||||
|
return -1, false
|
||||||
|
}
|
||||||
|
return l.FirstNode, true
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) NextId(id DllId) (DllId, bool) {
|
||||||
|
nextId := l.nodes[id].NextId
|
||||||
|
return nextId, nextId > -1
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) previousNode(node *DLLNode) *DLLNode {
|
||||||
|
if node.PreviousId != -1 {
|
||||||
|
return l.nodes[node.PreviousId]
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) nextNode(node *DLLNode) *DLLNode {
|
||||||
|
if node.NextId != -1 {
|
||||||
|
return l.nodes[node.NextId]
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) insertBetween(before *DLLNode, after *DLLNode, data T) (DllId, bool) {
|
||||||
|
if before == nil && after == nil {
|
||||||
|
return l.insertEmpty(data), true
|
||||||
|
}
|
||||||
|
if before == nil {
|
||||||
|
return l.InsertFirst(data), true
|
||||||
|
}
|
||||||
|
if after == nil {
|
||||||
|
return l.InsertLast(data), true
|
||||||
|
}
|
||||||
|
id := l.nextId()
|
||||||
|
node := standaloneNode(id)
|
||||||
|
l.data[id] = data
|
||||||
|
l.nodes[id] = node
|
||||||
|
node.PreviousId = before.Id
|
||||||
|
node.NextId = after.Id
|
||||||
|
before.NextId = id
|
||||||
|
after.PreviousId = id
|
||||||
|
|
||||||
|
l.length++
|
||||||
|
return id, true
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) GroupByInPlace(combineValues func(a, b T) (T, bool)) {
|
||||||
|
for node := l.nodes[l.FirstNode]; node.NextId > -1; node = l.nodes[node.NextId] {
|
||||||
|
|
||||||
|
if _, ok := combineValues(l.data[node.Id], l.data[node.NextId]); ok {
|
||||||
|
//l.InsertAfter(nodeId, combinedVal)
|
||||||
|
//toRemove = append(toRemove, nodeId)
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) FilterInPlace(predicate func(a T) bool) {
|
||||||
|
|
||||||
|
toRemove := make([]DllId, 0)
|
||||||
|
for node := range l.IterNodes() {
|
||||||
|
//node := l.nodes[nodeId]
|
||||||
|
if !predicate(l.data[node.Id]) {
|
||||||
|
toRemove = append(toRemove, node.Id)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
for _, id := range toRemove {
|
||||||
|
l.RemoveById(id)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (l *DoubleLinkedList[T]) RemoveById(id DllId) {
|
||||||
|
node := l.nodes[id]
|
||||||
|
|
||||||
|
if nextNode, nextOk := l.nodes[node.NextId]; nextOk {
|
||||||
|
nextNode.PreviousId = node.PreviousId
|
||||||
|
}
|
||||||
|
|
||||||
|
if prevNode, prevOk := l.nodes[node.PreviousId]; prevOk {
|
||||||
|
prevNode.NextId = node.NextId
|
||||||
|
}
|
||||||
|
delete(l.data, id)
|
||||||
|
delete(l.nodes, id)
|
||||||
|
l.length--
|
||||||
|
|
||||||
|
}
|
||||||
@@ -0,0 +1,6 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
const mockInput = "2333133121414131402"
|
||||||
|
|
||||||
|
const realInput = "704219278632287990157699389137759051173674176731519296433286809791368032791140804947394872662883692030734066918811375380315365946839884166725631883721349744981219785931738783661388125291795094512825242653511224344529672845877440596053786651997438268528266165877583264557764173257385107419113787961030843576369495156648607657305874974661342619859328104531363471956724144212686069472359909869782614837687412570278737636326532376654382479287314266216918399170381077374510753227602710837636353716486681754835117825158969402129114465198022264725519819115325335973411693168734904771142148782070387338504289387764846941276757746745106522138751194925533964573938179464827312306659599452182915973931773888255284375737997926166063489425643510644965438594524948703271505840402183767662574395756016552120135818566767138019941474772631862790487823438346257220408227416143679949374873323944606175885554784117984240628282969861642587588081316998464783302311604413776524659055292565694491379767947834223730617422333962111675807050666964389321334639586438406155526685126488178765415817948095855244321294582248756310796353956453907355968841584393107856349270912239245445715589273071788831214557439060709564134360881547651179958190879894701433432977738692207939989951915983551493776054681662557142987527678584259263554537304599324220506430594950518666862663426287835874324142262721579546211173304934736454912427662334184787558628937176161679602724891043375294218580214260739346464948698982798732241896854288538099187411137974746434901631692573606226429880181516389418796266327260298787325960361527581291481417404452522966443131663178394133589820212292125531411782759679271593462979437141634681896082138332462488207471444329946249767575323412321173378682686024796654481211784156405870857435221296571115105059339579779771904127212214793622528470337959644850728854513529262416401354682568543684424381483155574661933711845891836982753826366117317554416372728991717630823285403332223781684166753854111049563271766977755588836967112637337875355710285421601448195983751392386558364097653427771013512333833593951620492537122418536197142032197429592329277138227725983470686227236281764368754949204348228212248889854666234923201525292679528910224727888834476936652438789232826886705483509247528051817144277195596489299872419292568399107114809019791839804160715093262986248890759289248970648690442935895837508094937099202079462562903523808241416640891381152029339355699956653833661235215273361626383781213644195485944652613782964784847886255227238478917746987128382016919028687045545840857788827523152731968998587290441697505297184553688731517364462420224682709452324249129437229692911683466367248157866750208281448448858758248320514399157077264628152883875742796392967085854872212318367547462922934582983429745394204086136781676964255411753885534184652819315595923281988090159416521151799778192164804871698212699320118785439220363234964731728327545039908116278440961017446371498776478831583448219897956127565137548495232060416927745696717626204971354091384694999543701029819071565380298388685692323480576687205295205949816011989047865594892429735788347778389263811898225663745237592111587429814450211424511475453937107227621843707121213235532618661188695253384221792152811474149959729473701465666110311517608082355251679226465859591476368390869048839266517357219314235214172277111760224025144847157653618635887740687526311113662198204683324741748285708492444899419999541269128386362920652392378212156230723499176234166058463111802893731862696348199270948215487723342682203286217072601912332139478096333756155197483538433553795989784843548692325572866645614833335410539475473448451488982767578185956684218867531311417888583516262123688492883938971242284067238781464880991744952895768345519544465680332240484322708056752755295691196658597065202527347057139848428223625374173376951371446869596014538195459583827018333246562659135934819829768233413738478921955743403632627190188684941519144923353410578764984829487476413258822087327080841525901970865490939855946650986812258878522841476833679930117484496067455170512583899982118166977853966616999972681097989284115247683655371543823094434420854170492975368425883634606237316289989585317346186090978532841116122569897892786811873264996774247661178084491673357330799660728214636381487583557480343472204986901044511424151695271357362643383344953348413627971490283937893756531590434343425947386857677498831691532873721924504887143693888993371036479340956877775649911189538989822372485719724691248154598668533577701748988672147624698486251570993699627417815046611827692676861138752543754526869310889712106226424417595238568982799464478181571194963322609077715963508019313334643532775862329682646172504541559818775361509249732552562776118189488558263073218866584084799519626621294110958473298554262796269449315343723052802316509727556623764589966647137149732020553087304456628112311181126776596350734280533499495951652537203141613283665049455821677172639438128435173918Line truncated
|
||||||
|
const mediumInput = "7042192786322879901576993891377590511736741767315192964332868097913680327911408049473948726628836920307340669188113753803153659468398841667256318837213497449812197859317387836613881252917950945128252426535112243445296728458774405960537866519974382685282661658775832645577641732573851074191137879610308435763694951566486076573058749746613426198593281045313634719567241442126860694723599098697826148376874125702787376363265323766543824792873142662169183991703810773745107532276027108376363537164866817548351178251589694021291144651980222647255198191153253359734116931687349047711421487820703873385042893877648469412767577467451065221387511949255339645739381794648273123066595994521829159739317738882552843757379979261660634894256435106449654385945249487032715058404021837676625743957560165521201358185667671380199414747726318627904878234383462572204082274161436799493748733239446061758855547841179842406282829698616425875880813169984647833023116044137765246590552925656944913797679478342237306174223339621116758070506669643893213346395864384061555266851264881787654158179480958552443212945822487563107963539564539073559688415843931078563492709122392454457155892730717888312145574390607095641343608815476511799581908798947014334329777386922079399899519159835514937760546816625571429875276785842592635545373045993242205064305949505186668626634262878358743241422627215795462111733049347364549124276623341847875586289371761616796027248910433752942185802142607393464649486989827987322418968542885380991874111379747464349016316925736062264298801815163894187962663272602987873259603615275812914814174044525229664431316631783941335898202122921255314117827596792715934629794371416346818960821383324624882074714443299462497675753234123211733786826860247966544812117841564058708574352212965711151050593395797797719041272122147936225284703379596448507288545135292624164013546825685436844243814831555746619337118458918369827538263661173175544163727289917176308232854033322237816841667538541110495632717669777555888369671126373378753557102854216014481959837513923865583640976534277710135123338335939516204925371224185361971420321974295923292771382277259834706862272362817643687549492043482282122488898546662349232015252926795289102247278888344769366524387892328268867054835092475280518171442771955964892998724192925683991071148090197918398041607150932629862488907592892489706486904429358958375080949370992020794625629035238082414166408913811520293393556999566538336612352152733616263837812136441954859446526137829647848478862552272384789177469871283820169190286870455458408577888275231527319689985872904416975052971845536887315173644624202246827094523242491294372296929116834663672481578667502082814484488587582483205143991570772646281528838757427963929670858548722123183675474629229345829834297453942040861367816769642554117538855341846528193155959232819880901594165211517997781921648048716982126993201187854392203632349647317283275450399081162784409610174463714987764788315834482198979561275651375484952320604169277456967176262049713540913846949995437010298190715653802983886856923234805766872052952059498160119890478655948924297357883477783892638118982256637452375921115874298144502114245114754539371072276218437071212132355326186611886952533842217921528114741499597294737014656661103115176080823552516792264658595914763683908690488392665173572193142352141722771117602240251448471576536186358877406875263111136621982046833247417482857084924448994199995412691283863629206523923782121562307234991762341660584631118028937318626963481992709482154877233426822032862170726019123321394780963337561551974835384335537959897848435486923255728666456148333354105394754734484514889827675781859566842188675313114178885835162621236884928839389712422840672387814648809917449528957683455195444656803322404843227080567527552956911966585970652025273470571398484282236253741733769513714468695960145381954595838270183332465626591359348198297682334137384789219557434036326271901886849415191449233534105787649848294874764132588220873270808415259019708654909398559466509868122588785228414768336799301174844960674551705125838999821181669778539666169999726810979892841152476836553715438230944344208541704929753684258836346062373162899895853173461860909785328411161225698978927868118732649967742476611780844916733573307996607282146363814875835574803434722049869010445114241516952713573626433833449533484136279714902839378937565315904343434259473868576774988316915328737219245048871436938889933710364793409568777756499111895389898223724857197246912481545986685335777017489886721476246984862515709936996274178150466118276926768611387525437545268693108897121062264244175952385689827994644781815711949633226090777159635080193133346435327758623296826461725045415598187753615092497325525627761181894885582630732188665840847995196266212941109584732985542627962694493153437230528023165097275566237645899666471371497320205530873044566281123111811267765963507342805334994959516525372031416132836650494558216771726394381284351739Line truncated
|
||||||
@@ -0,0 +1,154 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"strconv"
|
||||||
|
"strings"
|
||||||
|
)
|
||||||
|
|
||||||
|
type Inode struct {
|
||||||
|
fileId int // inode with id -1 are empty
|
||||||
|
length int
|
||||||
|
}
|
||||||
|
|
||||||
|
func (inode *Inode) String() string {
|
||||||
|
v := ""
|
||||||
|
if inode.fileId < 0 {
|
||||||
|
v = "."
|
||||||
|
} else {
|
||||||
|
v = strconv.Itoa(inode.fileId)
|
||||||
|
}
|
||||||
|
return strings.Repeat(v, inode.length)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (inode *Inode) IsFreeSpace() bool {
|
||||||
|
return inode.fileId < 0
|
||||||
|
}
|
||||||
|
|
||||||
|
func (inode *Inode) Copy() *Inode {
|
||||||
|
return &Inode{inode.fileId, inode.length}
|
||||||
|
}
|
||||||
|
|
||||||
|
type FileSystem struct {
|
||||||
|
inodes *DoubleLinkedList[*Inode]
|
||||||
|
}
|
||||||
|
|
||||||
|
func (fs *FileSystem) String() string {
|
||||||
|
ret := ""
|
||||||
|
for inode := range fs.inodes.Iter() {
|
||||||
|
ret += inode.String()
|
||||||
|
}
|
||||||
|
return ret
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
func (fs *FileSystem) CheckSum() int {
|
||||||
|
ret, idx := 0, 0
|
||||||
|
for inode := range fs.inodes.Iter() {
|
||||||
|
if inode.IsFreeSpace() {
|
||||||
|
idx += inode.length
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
for j := 0; j < inode.length; j++ {
|
||||||
|
ret = ret + idx*inode.fileId
|
||||||
|
idx++
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return ret
|
||||||
|
}
|
||||||
|
|
||||||
|
func parseString(s string) *FileSystem {
|
||||||
|
dll := NewDLL[*Inode]()
|
||||||
|
inode := &Inode{-1, 0}
|
||||||
|
for _, c := range s {
|
||||||
|
fileId := -1
|
||||||
|
|
||||||
|
if c != '.' {
|
||||||
|
fileId, _ = strconv.Atoi(string(c))
|
||||||
|
}
|
||||||
|
if inode.fileId == fileId {
|
||||||
|
inode.length += 1
|
||||||
|
} else {
|
||||||
|
dll.InsertLast(inode)
|
||||||
|
inode = &Inode{fileId, 1}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
dll.InsertLast(inode)
|
||||||
|
if inode, ok := dll.Last(); !ok || !inode.IsFreeSpace() {
|
||||||
|
dll.InsertLast(&Inode{-1, 0})
|
||||||
|
}
|
||||||
|
return &FileSystem{dll}
|
||||||
|
}
|
||||||
|
|
||||||
|
func parseInput(input string) *FileSystem {
|
||||||
|
dll := NewDLL[*Inode]()
|
||||||
|
id := 0
|
||||||
|
for i, c := range input {
|
||||||
|
var inode *Inode
|
||||||
|
length, _ := strconv.Atoi(string(c))
|
||||||
|
if isFreeSpace := i%2 == 1; isFreeSpace {
|
||||||
|
inode = &Inode{-1, length}
|
||||||
|
} else {
|
||||||
|
inode = &Inode{id, length}
|
||||||
|
id++
|
||||||
|
}
|
||||||
|
dll.InsertLast(inode)
|
||||||
|
}
|
||||||
|
if inode, ok := dll.Last(); !ok || !inode.IsFreeSpace() {
|
||||||
|
dll.InsertLast(&Inode{-1, 0})
|
||||||
|
}
|
||||||
|
return &FileSystem{dll}
|
||||||
|
}
|
||||||
|
|
||||||
|
func (fs *FileSystem) takeFilesFromTheEnd(id DllId) *Inode {
|
||||||
|
for node, ok := fs.inodes.nodes[fs.inodes.LastNode]; ok; node, ok = fs.inodes.nodes[node.PreviousId] {
|
||||||
|
if node.Id == id {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
if inode, _ := fs.inodes.GetById(node.Id); !inode.IsFreeSpace() && inode.length > 0 {
|
||||||
|
return inode
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (fs *FileSystem) OptimizeDiskFragmentation() {
|
||||||
|
emptySpaceAtTheEndId, _ := fs.inodes.LastId()
|
||||||
|
emptySpaceAtTheEnd, _ := fs.inodes.Last()
|
||||||
|
for discId, ok := fs.inodes.FirstId(); ok; discId, ok = fs.inodes.NextId(discId) {
|
||||||
|
freeSpaceInode, _ := fs.inodes.GetById(discId)
|
||||||
|
if !freeSpaceInode.IsFreeSpace() || discId == emptySpaceAtTheEndId {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
fileInodeAtTheEnd := fs.takeFilesFromTheEnd(discId)
|
||||||
|
if fileInodeAtTheEnd == nil {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
|
||||||
|
if freeSpaceInode.length <= fileInodeAtTheEnd.length {
|
||||||
|
newInode := &Inode{fileInodeAtTheEnd.fileId, freeSpaceInode.length}
|
||||||
|
fs.inodes.InsertBefore(discId, newInode)
|
||||||
|
emptySpaceAtTheEnd.length += freeSpaceInode.length
|
||||||
|
fileInodeAtTheEnd.length -= freeSpaceInode.length
|
||||||
|
freeSpaceInode.length = 0
|
||||||
|
} else {
|
||||||
|
newFreeSpaceInode := &Inode{-1, freeSpaceInode.length - fileInodeAtTheEnd.length}
|
||||||
|
fs.inodes.InsertAfter(discId, newFreeSpaceInode)
|
||||||
|
fs.inodes.InsertBefore(discId, fileInodeAtTheEnd.Copy())
|
||||||
|
emptySpaceAtTheEnd.length += fileInodeAtTheEnd.length
|
||||||
|
fileInodeAtTheEnd.length = 0
|
||||||
|
freeSpaceInode.length = 0
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func Question9A(input string) int {
|
||||||
|
fs := parseInput(input)
|
||||||
|
fs.OptimizeDiskFragmentation()
|
||||||
|
return fs.CheckSum()
|
||||||
|
}
|
||||||
|
|
||||||
|
func main() {
|
||||||
|
fmt.Println("The answer to question 9A is: ", Question9A(realInput))
|
||||||
|
|
||||||
|
}
|
||||||
@@ -0,0 +1,73 @@
|
|||||||
|
package main
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestParseString(t *testing.T) {
|
||||||
|
input := "00.23"
|
||||||
|
fs := parseString(input)
|
||||||
|
if ret := fs.String(); ret != input {
|
||||||
|
t.Errorf("Expected %s received %s", input, ret)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestDefragmentize1(t *testing.T) {
|
||||||
|
fs := parseString("00..11")
|
||||||
|
fs.OptimizeDiskFragmentation()
|
||||||
|
expt := "0011.."
|
||||||
|
if ret := fs.String(); ret != expt {
|
||||||
|
t.Errorf("Expected %s received %s", expt, ret)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestDefragmentize2(t *testing.T) {
|
||||||
|
fs := parseString("00.112")
|
||||||
|
fs.OptimizeDiskFragmentation()
|
||||||
|
expt := "00211."
|
||||||
|
if ret := fs.String(); ret != expt {
|
||||||
|
t.Errorf("Expected %s received %s", expt, ret)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestDefragmentize3(t *testing.T) {
|
||||||
|
fs := parseString("00...112.")
|
||||||
|
fs.OptimizeDiskFragmentation()
|
||||||
|
expt := "00211...."
|
||||||
|
if ret := fs.String(); ret != expt {
|
||||||
|
t.Errorf("Expected %s received %s", expt, ret)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestDefragmentize4(t *testing.T) {
|
||||||
|
fs := parseString("00...111...2...333.44.5555.6666.777.888899")
|
||||||
|
fs.OptimizeDiskFragmentation()
|
||||||
|
expt := "0099811188827773336446555566.............."
|
||||||
|
if ret := fs.String(); ret != expt {
|
||||||
|
t.Errorf("Expected %s received %s", expt, ret)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestFilterInPlace(t *testing.T) {
|
||||||
|
dll := NewDLL[int]()
|
||||||
|
dll.InsertFirst(4)
|
||||||
|
dll.InsertFirst(3)
|
||||||
|
dll.InsertFirst(2)
|
||||||
|
dll.InsertFirst(1)
|
||||||
|
dll.FilterInPlace(func(x int) bool { return x%2 == 0 })
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestGroupByInPlace(t *testing.T) {
|
||||||
|
dll := NewDLL[int]()
|
||||||
|
dll.InsertFirst(4)
|
||||||
|
dll.InsertFirst(6)
|
||||||
|
dll.InsertFirst(3)
|
||||||
|
dll.InsertFirst(5)
|
||||||
|
dll.InsertFirst(2)
|
||||||
|
dll.GroupByInPlace(func(x, y int) (int, bool) {
|
||||||
|
if x%2 != y%2 {
|
||||||
|
return 0, false
|
||||||
|
}
|
||||||
|
return x + y, true
|
||||||
|
})
|
||||||
|
}
|
||||||
Reference in new issue
Block a user