Описание Банки, пытаясь увеличить свою прибыль, попросили инженеров разработать сканер, который автоматически считывает номера чеков. Известно, что любой чек имеет девятизначный номер и для каждого номера чека выполняется следующее условие: (d1+2·d2+...+9·d9) mod 11 = 0, где di равно i-й цифре номера (цифры нумеруются справа налево: d9d8d7d6d5d4d3d2d1) Сканер, считывая номер, преобразовывает горизонтальные и вертикальные линии в символы "|" (ASCII-код 124) и "_" (ASCII-код 95) соответственно. В результате сканирования выдается картинка, составленная из этих символов и пробелов. Пример правильного изображения цифр после сканирования приведен в примере входного файла Задача К сожалению, иногда сканер допускает ошибки, и некоторые линии могут пропадать. Вы должны написать программу, которая восстанавливает исходный номер чека, считая выполненными следующие условия:
Решение {$A+,B-,D+,E-,F-,G+,I+,L+,N+,O-,P-,Q-,R-,S-,T-,V+,X+,Y+} {$M 65520,0,655360} program scanner; const Chars:Array[0..9]Of Word=(2+8+32+64+128+256,32+256,2+16+32+64+128, 2+16+32+128+256,8+16+32+256,2+8+16+128+256, 2+8+16+64+128+256,2+32+256,2+8+16+32+64+128+256, 2+8+16+32+128+256); var Src:Array[1..9,0..2,0..2]Of Char; SrcB:Array[1..9]Of Word; Res:String; Procedure Load; Var I,J,K:Byte; St:String; Begin Assign(Input,'scanner.in'); ReSet(Input); For I:=0 To 2 Do Begin ReadLn(St); While Length(St)<27 Do St:=St+' '; For J:=1 To 9 Do For K:=0 To 2 Do Src[J,K,I]:=St[(J-1)*3+K+1]; End; Close(Input); End; Procedure Run; Var I,J,K:Byte; MayBe:Array[1..9,0..9]Of Boolean; Eq:Array[1..9]Of Byte; NotEq,NotEq1:Byte; Function Check:Boolean; Var I:Byte; Sum:LongInt; Begin Sum:=0; For I:=1 To 9 Do Sum:=Sum+I*Eq[10-I]; Check:=Sum Mod 11=0; End; Procedure MakeRes; Var I:Byte; Begin Res:=''; For I:=1 To 9 Do Res:=Res+Chr(Eq[I]+48); End; Begin NotEq:=0; For I:=1 To 9 Do Begin SrcB[I]:=0; For J:=0 To 2 Do For K:=0 To 2 Do SrcB[I]:=SrcB[I]+Ord((Src[I,J,K]='|') Or (Src[I,J,K]='_'))*(1 Shl (K*3+J)); Eq[I]:=10; For J:=0 To 9 Do Begin If SrcB[I]=Chars[J] Then Eq[I]:=J; MayBe[I,J]:=(SrcB[I] And Chars[J])=SrcB[I]; End; If Eq[I]=10 Then Begin Inc(NotEq); NotEq1:=I; End; End; Case NotEq Of 0:Begin If Check Then MakeRes Else Res:='failure'; For I:=1 To 9 Do Begin For J:=0 To 9 Do If (Eq[I]<>J) And MayBe[I,J] Then Begin K:=Eq[I]; Eq[I]:=J; If Check Then If Res='failure' Then MakeRes Else Begin Res:='ambiguous'; Exit; End; Eq[I]:=K; End; End; End; 1:Begin Res:='failure'; For J:=0 To 9 Do If MayBe[NotEq1,J] Then Begin Eq[NotEq1]:=J; If Check Then If Res='failure' Then MakeRes Else Begin Res:='ambiguous'; Exit; End; End; End; Else Res:='failure'; End; End; Procedure Save; Var I,J:Byte; Begin Assign(Output,'scanner.out'); ReWrite(Output); WriteLn(Res); Close(Output); End; Begin Load; Run; Save; End. |
© Особенности национальных задач по информатике |