Если кому-то интересно накиданное на коленке для проверки решение (без контроля входных параметров и обработки ошибок):
Код: Выделить всё
const
TIME_MOVE = 1;
TIME_READ = 1;
type
THDDState = record
Queue: Text;
TimeOut: Word;
Line, Time: LongInt;
Head: Byte;
end;
procedure InitHDD(var hdd: THDDState; aQueueName: String);
begin
FillChar(hdd, SizeOf(hdd), 0);
with hdd do begin
Assign(Queue, aQueueName);
ReSet(Queue);
ReadLn(Queue, TimeOut);
end;
end;
procedure DoneHDD(var hdd: THDDState);
begin
Close(hdd.Queue);
end;
procedure DeqLine(var hdd: THDDState);
var
track: byte;
begin
with hdd do begin
if Line * TimeOut > Time then Time := Line * TimeOut;
while not SeekEoLn(Queue) do begin
Read(Queue, track);
Inc(Time, abs(track - Head) * TIME_MOVE + TIME_READ);
Head := track;
end;
ReadLn(Queue);
Inc(Line);
end;
end;
var
hdd: THDDState;
begin
InitHDD(hdd, 'hdd.txt');
while not EoF(hdd.Queue) do DeqLine(hdd);
WriteLn('Total: ', hdd.Time);
DoneHDD(hdd);
end.
hdd.txt
Код: Выделить всё
100
50 10 250 30 10
20 40 20 10 60
15 10 25
51 11 251 31 11
21 41 21 11 61
Прогон:
В отличии от симулирования поквантового течения времени это решение использует прямой подсчёт затраченного времени, для учёта таймаутов опирается на номер строки в файле.
Добавлено спустя 16 минут 25 секунд:И вариант с отключаемой отладочной печатью:
Код: Выделить всё
{$DEFINE DEBPRINT}
const
TIME_MOVE = 1;
TIME_READ = 1;
{$IFDEF DEBPRINT}
Tracing: Boolean = True;
{$ENDIF}
type
THDDState = record
Queue: Text;
TimeOut: Word;
Line, Time: LongInt;
Head: Byte;
end;
procedure InitHDD(var hdd: THDDState; aQueueName: String);
begin
FillChar(hdd, SizeOf(hdd), 0);
with hdd do begin
Assign(Queue, aQueueName);
ReSet(Queue);
ReadLn(Queue, TimeOut);
{$IFDEF DEBPRINT}
if Tracing then WriteLn(stderr, '* Queue timeout: ', TimeOut);
{$ENDIF}
end;
end;
procedure DoneHDD(var hdd: THDDState);
begin
Close(hdd.Queue);
end;
procedure DeqLine(var hdd: THDDState);
var
track: byte;
begin
with hdd do begin
if Line * TimeOut > Time then begin
{$IFDEF DEBPRINT}
if Tracing then WriteLn(stderr, '* ', Line, ',', Time, ': Timeout to ', Line * TimeOut);
{$ENDIF}
Time := Line * TimeOut;
end;
while not SeekEoLn(Queue) do begin
Read(Queue, track);
{$IFDEF DEBPRINT}
if Tracing then WriteLn(stderr, '* ', Line, ',', Time, ': ', Head, '->', track, ', ', abs(track - Head) * TIME_MOVE, '+', TIME_READ);
{$ENDIF}
Inc(Time, abs(track - Head) * TIME_MOVE + TIME_READ);
Head := track;
end;
ReadLn(Queue);
Inc(Line);
end;
end;
var
hdd: THDDState;
begin
InitHDD(hdd, 'hdd.txt');
while not EoF(hdd.Queue) do DeqLine(hdd);
WriteLn('Total: ', hdd.Time);
DoneHDD(hdd);
end.
На "облегчённой" очереди:
Код: Выделить всё
100
50
20 40 20 10 60
15 10 25
51 11 251 31 11
21 41 21 11 61
получается что-то вроде:
Код: Выделить всё
* Queue timeout: 100
* 0,0: 0->50, 50+1
* 1,51: Timeout to 100
* 1,100: 50->20, 30+1
* 1,131: 20->40, 20+1
* 1,152: 40->20, 20+1
* 1,173: 20->10, 10+1
* 1,184: 10->60, 50+1
* 2,235: 60->15, 45+1
* 2,281: 15->10, 5+1
* 2,287: 10->25, 15+1
* 3,303: 25->51, 26+1
* 3,330: 51->11, 40+1
* 3,371: 11->251, 240+1
* 3,612: 251->31, 220+1
* 3,833: 31->11, 20+1
* 4,854: 11->21, 10+1
* 4,865: 21->41, 20+1
* 4,886: 41->21, 20+1
* 4,907: 21->11, 10+1
* 4,918: 11->61, 50+1
Total: 969