рд╣рд╛рд╕реНрдХреЗрд▓ рдореЗрдВ рдЬрд╛рдкрд╛рдиреА рдХреНрд░реЙрд╕рд╡рд░реНрдб рд╕рдорд╛рдзрд╛рди

рдЬрд╛рдкрд╛рдиреА рдХреНрд░реЙрд╕рд╡рд░реНрдб рдкрд╣реЗрд▓реА рдПрдХ рдкрд╣реЗрд▓реА рд╣реИ, рдЬрд┐рд╕рдореЗрдВ рд╕рдВрдЦреНрдпрд╛рдУрдВ рдХреЗ рдПрдХ рд╕реЗрдЯ рдХрд╛ рдЙрдкрдпреЛрдЧ рдХрд░рдХреЗ, рдЖрдкрдХреЛ рдореВрд▓ рдХрд╛рд▓реЗ рдФрд░ рд╕рдлреЗрдж рдЫрд╡рд┐ рдХреЛ рдлрд┐рд░ рд╕реЗ рдмрдирд╛рдирд╛ рд╣реЛрдЧрд╛ред рдкрд┐рдХреНрд╕реЗрд▓ рдХреА рдкреНрд░рддреНрдпреЗрдХ рдкрдВрдХреНрддрд┐ рдФрд░ рдкреНрд░рддреНрдпреЗрдХ рдХреЙрд▓рдо рдХрд╛ рдЕрдкрдирд╛ рд╕реЗрдЯ рд╣реЛрддрд╛ рд╣реИ, рдЬрд┐рд╕рдореЗрдВ рдкреНрд░рддреНрдпреЗрдХ рд╕рдВрдЦреНрдпрд╛, рдмрджрд▓реЗ рдореЗрдВ, рд▓рдЧрд╛рддрд╛рд░ рдХрд╛рд▓реЗ рдкрд┐рдХреНрд╕реЗрд▓ рдХреЗ рдмреНрд▓реЙрдХ рдХреА рд▓рдВрдмрд╛рдИ рд╕реЗ рдореЗрд▓ рдЦрд╛рддреА рд╣реИред рдРрд╕реЗ рдмреНрд▓реЙрдХреЛрдВ рдХреЗ рдмреАрдЪ рдХрдо рд╕реЗ рдХрдо рдПрдХ рд╕рдлреЗрдж рдкрд┐рдХреНрд╕реЗрд▓ рд╣реЛрдирд╛ рдЪрд╛рд╣рд┐рдП, рд▓реЗрдХрд┐рди рдЙрдирдХреА рд╕рд╣реА рд╕рдВрдЦреНрдпрд╛ рдЬреНрдЮрд╛рдд рдирд╣реАрдВ рд╣реИред рдЗрди рдкрд╣реЗрд▓рд┐рдпреЛрдВ рдХреЗ рд▓рд┐рдП рдкреВрд░реА рддрд░рд╣ рд╕реЗ рд╕рдорд░реНрдкрд┐рдд рдкрддреНрд░рд┐рдХрд╛рдПрдБ рдЕрдзрд┐рдХрд╛рдВрд╢ рд╕рдорд╛рдЪрд╛рд░рдкрддреНрд░реЛрдВ рдореЗрдВ рдкрд╛рдИ рдЬрд╛рддреА рд╣реИрдВ, рдЗрд╕рд▓рд┐рдП рдореБрдЭреЗ рд▓рдЧрддрд╛ рд╣реИ рдХрд┐ рдЙрдирдореЗрдВ рд╕реЗ рд▓рдЧрднрдЧ рд╕рднреА рдХрдо рд╕реЗ рдХрдо рдПрдХ рдмрд╛рд░ рдорд┐рд▓ рдЪреБрдХреЗ рд╣реИрдВ, рдФрд░ рдЗрд╕рд▓рд┐рдП рдЕрдзрд┐рдХ рд╡рд┐рд╕реНрддреГрдд рд╡рд┐рд╡рд░рдг рдХреЛ рдпрд╣рд╛рдВ рдЫреЛрдбрд╝рд╛ рдЬрд╛ рд╕рдХрддрд╛ рд╣реИ ред

рдХреБрдЫ рдмрд┐рдВрджреБ рдкрд░, рдореИрдВ "рдХрдВрдкреНрдпреВрдЯрд░ рд╕рд┐рдЦрд╛рдирд╛" рдЪрд╛рд╣рддрд╛ рдерд╛ рдХрд┐ рдЬрд╛рдкрд╛рдиреА рдХреНрд░реЙрд╕рд╡рд░реНрдб рдХреЛ рдХреИрд╕реЗ рд╣рд▓ рдХрд┐рдпрд╛ рдЬрд╛рдП рдХреНрдпреЛрдВрдХрд┐ рдореИрдВ рдЦреБрдж рдЙрдиреНрд╣реЗрдВ рд╣рд▓ рдХрд░рддрд╛ рд╣реВрдВред рдХреЛрдИ рдмреБрд▓рдВрдж рд▓рдХреНрд╖реНрдп рдирд╣реАрдВ, рд╕рд┐рд░реНрдл рдордиреЛрд░рдВрдЬрди рдХреЗ рд▓рд┐рдПред рддрдм рддрд░реАрдХреЗ рдЬреЛрдбрд╝реЗ рдЧрдП рдереЗ рдХрд┐ рдореИрдВ рдЦреБрдж рдорд╛рдирд╡ рдорд╕реНрддрд┐рд╖реНрдХ рдХреА рд╕реАрдорд┐рдд рдХреНрд╖рдорддрд╛рдУрдВ рдХреЗ рдХрд╛рд░рдг рдЖрд╡реЗрджрди рдирд╣реАрдВ рдХрд░ рд╕рдХрддрд╛, рд▓реЗрдХрд┐рди, рдирд┐рд╖реНрдкрдХреНрд╖рддрд╛ рдореЗрдВ, рдХрд╛рд░реНрдпрдХреНрд░рдо рдЙрдирдХреЗ рдмрд┐рдирд╛ рдкрддреНрд░рд┐рдХрд╛рдУрдВ рд╕реЗ рд╕рднреА рд╡рд░реНрдЧ рдкрд╣реЗрд▓реА рдХреЗ рд╕рд╛рде рдореБрдХрд╛рдмрд▓рд╛ рдХрд░рддрд╛ рд╣реИред

рддреЛ, рдХрд╛рд░реНрдп рд╕рд░рд▓ рд╣реИ: рдПрдХ рдкрд╣реЗрд▓реА рдкрд╣реЗрд▓реА рдХреЛ рд╣рд▓ рдХрд░реЗрдВ, рдФрд░ рдпрджрд┐ рдХрдИ рд╕рдорд╛рдзрд╛рди рд╣реИрдВ, рддреЛ рдЙрди рд╕рднреА рдХреЛ рдвреВрдВрдвреЗрдВред рд╕рдорд╛рдзрд╛рди рд╣рд╛рд╕реНрдХреЗрд▓ рдореЗрдВ рд▓рд┐рдЦрд╛ рдЧрдпрд╛ рд╣реИ, рдФрд░ рдпрджреНрдпрдкрд┐ рдХреЛрдб рдкрд░реНрдпрд╛рдкреНрдд рд░реВрдк рд╕реЗ рдореМрдЦрд┐рдХ рд╡рд┐рд╡рд░рдг рдХрд╛ рдЕрдиреБрдкрд╛рд▓рди рдХрд░рддрд╛ рд╣реИ, рдпрд╣рд╛рдВ рддрдХ тАЛтАЛрдХрд┐ рднрд╛рд╖рд╛ рдХреЗ рдЬреНрдЮрд╛рди рдХреЗ рдмрд┐рдирд╛, рд╕рд╛рдорд╛рдиреНрдп рд╕рд╛рд░ рдХреЛ рд╕рдордЭрд╛ рдЬрд╛ рд╕рдХрддрд╛ рд╣реИред рдпрджрд┐ рдЖрдк рдкрд░рд┐рдгрд╛рдо рдХреЛ рд▓рд╛рдЗрд╡ рдорд╣рд╕реВрд╕ рдХрд░рдирд╛ рдЪрд╛рд╣рддреЗ рд╣реИрдВ, рддреЛ рдкреНрд░реЛрдЬреЗрдХреНрдЯ рдкреГрд╖реНрда рдкрд░ рдЖрдк рд╕реНрд░реЛрдд рдХреЛрдб рдбрд╛рдЙрдирд▓реЛрдб рдХрд░ рд╕рдХрддреЗ рд╣реИрдВ (рдореИрдВрдиреЗ рдмрд╛рдЗрдирд░реА рдЕрд╕реЗрдВрдмрд▓реА рдЕрдкрд▓реЛрдб рдирд╣реАрдВ рдХреА рдереА)ред рд╕рдорд╛рдзрд╛рди рдмрд╛рдЗрдирд░реА рдкреАрдмреАрдПрдо рдХреЛ рдирд┐рд░реНрдпрд╛рдд рдХрд┐рдП рдЬрд╛рддреЗ рд╣реИрдВ, рдФрд░ рдЖрдк рдЗрд╕рд╕реЗ рд╢рд░реНрддреЛрдВ рдХреЛ рдирд┐рдХрд╛рд▓ рд╕рдХрддреЗ рд╣реИрдВред



рдЗрд╕ рддрдереНрдп рдХреЗ рдмрд╛рд╡рдЬреВрдж рдХрд┐ рдореИрдВрдиреЗ рдпрдерд╛рд╕рдВрднрд╡ рд╕реНрдкрд╖реНрдЯ рд░реВрдк рд╕реЗ рд▓рд┐рдЦрдиреЗ рдХреА рдХреЛрд╢рд┐рд╢ рдХреА, рдореИрдВ рдкреВрд░реА рддрд░рд╣ рд╕реЗ рд╕рдлрд▓ рдирд╣реАрдВ рд╣реБрдЖред рдХрдЯ рдХреЗ рддрд╣рдд рдмрд╣реБрдд рд╕рд╛рд░реЗ рдкрддреНрд░ рдФрд░ рдХреЛрдб рдФрд░ рд▓рдЧрднрдЧ рдХреЛрдИ рдЪрд┐рддреНрд░ рдирд╣реАрдВред

bitmask


рдкреВрд░рд╛ рдХрд╛рд░реНрдпрдХреНрд░рдо рдПрдХ рдмрд┐рдЯ рдорд╛рд╕реНрдХ рдХреЗ рд▓рд┐рдП рдЖрдкрдХреА рдмрд╛рдЗрдХ рдкрд░ рдЖрдзрд╛рд░рд┐рдд рд╣реИред рдпрд╣ рдмрд╣реБрдд рддреЗрдЬрд╝ рдирд╣реАрдВ рд╣реИ, рд▓реЗрдХрд┐рди рдЗрд╕рдореЗрдВ рдПрдХ рд╕рдВрдкрддреНрддрд┐ рд╣реИ рдЬреЛ рдбрд┐рдмрдЧрд┐рдВрдЧ рдкреНрд░рдХреНрд░рд┐рдпрд╛ рдореЗрдВ рдореЗрд░реЗ рд▓рд┐рдП рдорд╣рддреНрд╡рдкреВрд░реНрдг рдереА: рдпрд╣ рдЙрди рдСрдкрд░реЗрд╢рдиреЛрдВ рдХреЗ рджреМрд░рд╛рди рджреБрд░реНрдШрдЯрдирд╛рдЧреНрд░рд╕реНрдд рд╣реЛ рдЬрд╛рддреА рд╣реИ рдЬреЛ рдЕрд▓рдЧ-рдЕрд▓рдЧ рд▓рдВрдмрд╛рдИ рдХреЗ рдореБрдЦреМрдЯреЗ рдкрд░ рдХрд┐рд╕реА рднреА рдСрдкрд░реЗрд╢рди рдХреЗ рджреМрд░рд╛рди, рдЗрд╕рдХрд╛ рдХреЛрдИ рдорддрд▓рдм рдирд╣реАрдВ рд╣реИред рдореИрдВ рдпрд╣рд╛рдВ рдХреЗрд╡рд▓ рдХрд╛рд░реНрдпреЛрдВ рдХреЗ рд╣рд╕реНрддрд╛рдХреНрд╖рд░ рдФрд░ рдЙрдирдХреЗ рдХрд╛рдо рдХреЗ рд╕рд┐рджреНрдзрд╛рдВрдд рдХреЛ рд╕рдордЭрд╛рддреЗ рд╣реБрдП рдЪрд┐рддреНрд░ рджреВрдВрдЧрд╛; рдХрд╛рд░реНрдпрд╛рдиреНрд╡рдпрди рдмрд╣реБрдд рд╣реА рдЖрджрд┐рдо рд╣реИ рдФрд░ рдЗрд╕рдХрд╛ рд╕рдорд╛рдзрд╛рди рд╕реЗ рдХреЛрдИ рд╕реАрдзрд╛ рд╕рдВрдмрдВрдз рдирд╣реАрдВ рд╣реИред

bmCreate :: Int -> BitMask bmLength :: BitMask -> Int bmSize :: BitMask -> Int bmIsEmpty :: BitMask -> Bool bmNot :: BitMask -> BitMask bmAnd :: BitMask -> BitMask -> BitMask bmOr :: BitMask -> BitMask -> BitMask bmIntersection :: [BitMask] -> BitMask bmUnion :: [BitMask] -> BitMask bmSplit :: BitMask -> [BitMask] bmByOne :: BitMask -> [BitMask] bmExpand :: BitMask -> BitMask bmFillGaps :: BitMask -> BitMask bmLeftIncursion :: Int -> BitMask -> BitMask bmRightIncursion :: Int -> BitMask -> BitMask bmTranspose :: [BitMask] -> [BitMask] 



рдореБрдЭреЗ рд▓рдЧрддрд╛ рд╣реИ рдХрд┐ рдЗрд╕ рддрд░рд╣ рдХреЗ рдПрдХ рдЧреНрд░рд╛рдлрд┐рдХрд▓ рд╡рд┐рд╡рд░рдг рдХреЛ рдЫреЛрдбрд╝рдХрд░ рд╕рднреА рдХрд╛рд░реНрдпреЛрдВ рдХреЗ рд▓рд┐рдП рд╕рдВрдкреВрд░реНрдг рд╣реИ, рд╢рд╛рдпрдж, bmLeftIncursion рдФрд░ bmRightIncursion ред рдЙрдиреНрд╣реЗрдВ рдХреНрдпреЛрдВ рдЖрд╡рд╢реНрдпрдХ рд╣реИ, рдпрд╣ рдмрд╛рдж рдореЗрдВ рд╕реНрдкрд╖реНрдЯ рд╣реЛрдЧрд╛, рдЙрдирдХреЗ рдХрд╛рдо рдХрд╛ рд╕рд┐рджреНрдзрд╛рдВрдд рдЗрд╕ рдкреНрд░рдХрд╛рд░ рд╣реИ: bmLeftIncursion рд╕рдмрд╕реЗ рдмрд╛рдИрдВ рдУрд░ рднрд░рд╛ bmLeftIncursion рдкрд╛рддрд╛ рд╣реИ рдФрд░ рдПрдХ рдореБрдЦреМрдЯрд╛ рдмрдирд╛рддрд╛ рд╣реИ рдЬрд┐рд╕рдореЗрдВ рд╕рднреА рдмрд┐рдЯреНрд╕ рдЗрд╕рдХреЗ рдкрд╣рд▓реЗ рднрд░реЗ рдЬрд╛рддреЗ рд╣реИрдВ, рд╕рд╛рде рд╣реА рд╕рд╛рде рдХрдИ рдмрд┐рдЯреНрд╕ рд╕реЗ рд╢реБрд░реВ рд╣реЛрддрд╛ рд╣реИ рдЬрдм рдлрд╝рдВрдХреНрд╢рди рдХреЛ рдирд┐рд░реНрджрд┐рд╖реНрдЯ рдХрд┐рдпрд╛ рдЧрдпрд╛ рдерд╛; рджреВрд╕рд░рд╛ рдлрд╝рдВрдХреНрд╢рди рд╕рдорд╛рди рд░реВрдк рд╕реЗ рдХрд╛рдо рдХрд░рддрд╛ рд╣реИред

рд╕рдВрд░рдЪрдирд╛


рдЪреВрдВрдХрд┐ рдХреНрд░реЙрд╕рд╡рд░реНрдб рдХрд╛ рд╣рд▓ рд▓рд╛рдЗрдиреЛрдВ рдХреЗ рд╕рд╛рде рд╣реЛрддрд╛ рд╣реИ, рдкреВрд░реЗ рдХреНрд╖реЗрддреНрд░ рдХреЗ рдЕрдиреБрд░реВрдк рдкреНрд░рдХрд╛рд░ рд╕рднреА рдХреНрд╖реИрддрд┐рдЬ рдФрд░ рдКрд░реНрдзреНрд╡рд╛рдзрд░ рд▓рд╛рдЗрдиреЛрдВ рдХрд╛ рдПрдХ рд╕реЗрдЯ рд╣реЛрддрд╛ рд╣реИ, рд╣рд╛рд▓рд╛рдВрдХрд┐ рдЗрд╕рд╕реЗ рдХреНрд░реЙрд╕рд╡рд░реНрдб рдХреА рд╕рднреА рдХреЛрд╢рд┐рдХрд╛рдУрдВ рдХрд╛ рджреЛрд╣рд░рд╛рд╡ рд╣реЛрддрд╛ рд╣реИред

 data Field = Field { flHorLines :: [Line], flVerLines :: [Line] } deriving Eq 

рдкреНрд░рддреНрдпреЗрдХ рдкрдВрдХреНрддрд┐ рдХреЛрд╢рд┐рдХрд╛рдУрдВ рдФрд░ рдмреНрд▓реЙрдХреЛрдВ рдХреЗ рдмрд╛рд░реЗ рдореЗрдВ рдЬрд╛рдирдХрд╛рд░реА рд╕рдВрдЧреНрд░рд╣реАрдд рдХрд░рддреА рд╣реИ (рдПрдХ рдмреНрд▓реЙрдХ рдПрдХ рд╕реНрдерд┐рддрд┐ рдореЗрдВ рдПрдХ рд╕рдВрдЦреНрдпрд╛ рд╕реЗ рдореЗрд▓ рдЦрд╛рддреА рд╣реИ)ред

 data Line = Line { lnMask :: LineMask, lnBlocks :: [Block] } deriving Eq 

рдХреЛрд╢рд┐рдХрд╛рдУрдВ рдХреЗ рдмрд╛рд░реЗ рдореЗрдВ рдЬрд╛рдирдХрд╛рд░реА рдПрдХ рд╣реА рд▓рдВрдмрд╛рдИ рдХреЗ рджреЛ рдмрд┐рдЯ рдорд╛рд╕реНрдХ рдХреЗ рд░реВрдк рдореЗрдВ рд╕рдВрдЧреНрд░рд╣реАрдд рд╣реЛрддреА рд╣реИ, рдЬреЛ рднрд░реЗ рдФрд░ рдЕрд╡рд░реБрджреНрдз рдХреЛрд╢рд┐рдХрд╛рдУрдВ рдХрд╛ рдкреНрд░рддрд┐рдирд┐рдзрд┐рддреНрд╡ рдХрд░рддреА рд╣реИред

 data LineMask = LineMask { lmFilledMask :: BitMask, lmBlockedMask :: BitMask } deriving Eq 

рдмреНрд▓реЙрдХ, рд╕рдВрдЦреНрдпрд╛ рдХреЗ рдЕрд▓рд╛рд╡рд╛, рдЗрд╕рдореЗрдВ рдПрдХ рдореБрдЦреМрдЯрд╛ рд╣реЛрддрд╛ рд╣реИ рдЬреЛ рдЙрд╕ рд░реЗрдЦрд╛ рдХреЗ рдХреНрд╖реЗрддреНрд░ рд╕реЗ рдореЗрд▓ рдЦрд╛рддрд╛ рд╣реИ рдЬрд┐рд╕рдореЗрдВ рдпрд╣ рдмреНрд▓реЙрдХ рд╣реЛ рд╕рдХрддрд╛ рд╣реИред

 data Block = Block { blScopeMask :: BitMask, blNumber :: Int } deriving Eq 

рд╕рдорд╛рдзрд╛рди рдХреА рд╢реБрд░реБрдЖрдд рдореЗрдВ, рднрд░реЗ рдФрд░ рдЕрд╡рд░реБрджреНрдз рдХреЛрд╢рд┐рдХрд╛рдУрдВ рдХреЗ рдорд╛рд╕реНрдХ рдЦрд╛рд▓реА рд╣реЛрддреЗ рд╣реИрдВ, рдФрд░ рдмреНрд▓реЙрдХ рдХрд╛ рдореБрдЦреМрдЯрд╛, рдЗрд╕рдХреЗ рд╡рд┐рдкрд░реАрдд, рдкреВрд░реА рддрд░рд╣ рд╕реЗ рднрд░рд╛ рд╣реЛрддрд╛ рд╣реИред рдЗрд╕рдХрд╛ рдорддрд▓рдм рд╣реИ рдХрд┐ рд╕рднреА рдХреЛрд╢рд┐рдХрд╛рдПрдВ рдЦрд╛рд▓реА рд╣реИрдВ, рдФрд░ рдкреНрд░рддреНрдпреЗрдХ рдмреНрд▓реЙрдХ рд▓рд╛рдЗрди рдХреЗ рдХрд┐рд╕реА рднреА рд╣рд┐рд╕реНрд╕реЗ рдореЗрдВ рд╣реЛ рд╕рдХрддрд╛ рд╣реИред рд╕рдорд╛рдзрд╛рди рдкреНрд░рдХреНрд░рд┐рдпрд╛ рдкреНрд░рддреНрдпреЗрдХ рдмреНрд▓реЙрдХ рдХреЗ рдХреНрд╖реЗрддреНрд░рдлрд▓ рдХреЛ рдЙрд╕рдХреА рд╕рдВрдЦреНрдпрд╛ рдХреЗ рдмрд░рд╛рдмрд░ рдЖрдХрд╛рд░ рджреЗрдиреЗ рдФрд░ рдорд╛рд╕реНрдХ рдХреЗ рдЕрдиреБрд╕рд╛рд░ рднрд░рдиреЗ рдХреЗ рд▓рд┐рдП рдиреАрдЪреЗ рдЖрддреА рд╣реИред

рдкреВрд░реНрдгрддрд╛ рдФрд░ рд╕рд┐рдВрдХреНрд░рдирд╛рдЗрдЬрд╝реЗрд╢рди

рдЙрдкрд░реЛрдХреНрдд рд╕рднреА рдкреНрд░рдХрд╛рд░ ( BitMask рдХреЛ рдЫреЛрдбрд╝рдХрд░) рджреЛ рд╡рд░реНрдЧреЛрдВ рдХреЗ рдЙрджрд╛рд╣рд░рдг рд╣реИрдВ: Syncable рдФрд░ Syncable ред

Completable рдХреНрд▓рд╛рд╕ рдХрд╛ рдПрдХрдорд╛рддреНрд░ рдлрд╝рдВрдХреНрд╢рди рдХрд┐рд╕реА рдСрдмреНрдЬреЗрдХреНрдЯ рдХреА "рдкреВрд░реНрдгрддрд╛" рджрд┐рдЦрд╛рддрд╛ рд╣реИред рдПрдХ рдлрд╝реАрд▓реНрдб рдХреЛ рдкреВрд░рд╛ рдорд╛рдирд╛ рдЬрд╛рддрд╛ рд╣реИ рдпрджрд┐ рдЙрд╕рдХреА рд╕рднреА рд▓рд╛рдЗрдиреЗрдВ рдкреВрд░реА рд╣реЛ рдЬрд╛рддреА рд╣реИрдВред рдПрдХ рдкрдВрдХреНрддрд┐ рдкреВрд░реА рд╣реЛ рдЬрд╛рддреА рд╣реИ рдЕрдЧрд░ рдЙрд╕рдХреЗ рд╕рднреА рдмреНрд▓реЙрдХ рдкреВрд░реЗ рд╣реЛ рдЬрд╛рддреЗ рд╣реИрдВ; рдЙрд╕реА рд╕рдордп, рдЕрдирд╛рд╡рд╢реНрдпрдХ рд░реВрдк рд╕реЗ рдореБрдЦреМрдЯрд╛ рдХреЛ рдкреВрд░рд╛ рдХрд░рдирд╛ рдЖрд╡рд╢реНрдпрдХ рд╣реИ (рдпрд╣ рдмреНрд▓реЙрдХреЛрдВ рдХреА рдкреВрд░реНрдгрддрд╛ рд╕реЗ рдирд┐рдореНрдирд╛рдиреБрд╕рд╛рд░ рд╣реИ; рдХреНрдпреЛрдВ, рдлрд┐рд░ рд╕реЗ, рдпрд╣ рдереЛрдбрд╝реА рджреЗрд░ рдмрд╛рдж рд╕реНрдкрд╖реНрдЯ рд╣реЛрдЧрд╛)ред рдмреНрд▓реЙрдХ рдХреЛ рдкреВрд░рд╛ рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП, рдЬреИрд╕рд╛ рдХрд┐ рдКрдкрд░ рдЙрд▓реНрд▓реЗрдЦ рдХрд┐рдпрд╛ рдЧрдпрд╛ рд╣реИ, рдпрд╣ рдЖрд╡рд╢реНрдпрдХ рд╣реИ рдХрд┐ рдЗрд╕рдХреЗ рдХреНрд╖реЗрддреНрд░ рдХрд╛ рдЖрдХрд╛рд░ рдЗрд╕рдХреА рд╕рдВрдЦреНрдпрд╛ рдХреЗ рд╕рд╛рде рдореЗрд▓ рдЦрд╛рддрд╛ рд╣реЛред

 class Completable a where clIsCompleted :: a -> Bool instance Completable Field where clIsCompleted fl = all clIsCompleted (flHorLines fl) && all clIsCompleted (flVerLines fl) instance Completable Line where clIsCompleted ln = all clIsCompleted (lnBlocks ln) instance Completable Block where clIsCompleted bl = bmSize (blScopeMask bl) == blNumber bl 

Syncable рд╡рд░реНрдЧ рдлрд╝рдВрдХреНрд╢рдВрд╕ рдкреНрд░рджрд╛рди рдХрд░рддрд╛ рд╣реИ рдЬреЛ рдЖрдкрдХреЛ рд╡рд┐рднрд┐рдиреНрди рдирд┐рд░реНрдгрдп рд╢рд╛рдЦрд╛рдУрдВ рдХреЛ рдПрдХ рд╕рд╛рде рд▓рд╛рдиреЗ рджреЗрддрд╛ рд╣реИред snAverage рдХреЗрд╡рд▓ рджреЛ рд╢рд╛рдЦрд╛рдУрдВ рд╕реЗ рд╕рд╛рдорд╛рдиреНрдп рдХреЛ рдирд┐рдХрд╛рд▓рддрд╛ рд╣реИ, рдФрд░ snSync - рдЬреЛ рдХрдо рд╕реЗ рдХрдо рдПрдХ рд╢рд╛рдЦрд╛ рдореЗрдВ рджрд┐рдЦрд╛рдИ рджреЗрддрд╛ рд╣реИ (рд╣рдо рдЙрдиреНрд╣реЗрдВ рдХреНрд░рдорд╢рдГ bmAnd рдФрд░ bmOr рд╕рд╛рдорд╛рдиреНрдпреАрдХрд░рдг рдкрд░ рд╡рд┐рдЪрд╛рд░ рдХрд░ рд╕рдХрддреЗ рд╣реИрдВ)ред snAverageAll рдФрд░ snSyncAll рдмрд┐рд▓реНрдХреБрд▓ рдПрдХ рд╣реА рдХрд╛рдо рдХрд░рддреЗ рд╣реИрдВ, рд▓реЗрдХрд┐рди рд╡реЗ рджреЛ рд╡рд╕реНрддреБрдУрдВ рдХреЗ рд╕рд╛рде рдирд╣реАрдВ, рдмрд▓реНрдХрд┐ рд╡рд╕реНрддреБрдУрдВ рдХреА рд╕реВрдЪреА рдХреЗ рд╕рд╛рде рдХрд╛рдо рдХрд░рддреЗ рд╣реИрдВред

 class Syncable a where snSync :: a -> a -> Maybe a sn1 `snSync` sn2 = snSyncAll [sn1, sn2] snAverage :: a -> a -> Maybe a sn1 `snAverage` sn2 = snAverageAll [sn1, sn2] snSyncAll :: [a] -> Maybe a snSyncAll [] = Nothing snSyncAll sns = foldr1 (wrap snSync) (map return sns) snAverageAll :: [a] -> Maybe a snAverageAll [] = Nothing snAverageAll sns = foldr1 (wrap snAverage) (map return sns) wrap :: Monad m => (a -> b -> mc) -> ma -> mb -> mc wrap f mx my = do x <- mx y <- my fxy 

рд╕рдВрдЧрддрд┐

Syncable рдХреНрд▓рд╛рд╕ рдХреЗ рдХрд╛рд░реНрдпреЛрдВ рдХреЗ рд╡рд┐рд╡рд░рдг рд╕реЗ, Syncable рджреЗрдЦрд╛ рдЬрд╛ рд╕рдХрддрд╛ рд╣реИ рдХрд┐ рдЙрдирдХрд╛ рдкрд░рд┐рдгрд╛рдо Maybe рдореЛрдирдб рдореЗрдВ рд▓рд┐рдкрдЯреА рд╣реБрдИ рд╡рд╕реНрддреБ рд╣реИред рд╡рд╛рд╕реНрддрд╡ рдореЗрдВ, рдпрд╣ рдЗрд╕ рдкреНрд░рдХрд╛рд░ рд╣реИ рдХрд┐ рд╕рдВрдЧрддрд┐ рдХреА рдорд╣рддреНрд╡рдкреВрд░реНрдг рдЕрд╡рдзрд╛рд░рдгрд╛ рд╕реНрд╡рдпрдВ рдкреНрд░рдХрдЯ рд╣реЛрддреА рд╣реИ, рдЬреЛ рдЙрдкрд░реЛрдХреНрдд рд╕рднреА рдкреНрд░рдХрд╛рд░реЛрдВ рдХреЗ рд▓рд┐рдП рднреА рдкрд░рд┐рднрд╛рд╖рд┐рдд рд╣реИ, рд▓реЗрдХрд┐рди рдЗрдирдХреИрдкреНрд╕реБрд▓реЗрд╢рди рдХрд╛рд░рдгреЛрдВ рдХреЗ рд▓рд┐рдП рдПрдХ рдЕрд▓рдЧ рд╡рд░реНрдЧ рдореЗрдВ рдирд╣реАрдВ рд▓реЗ рдЬрд╛рдпрд╛ рдЧрдпрд╛ рд╣реИред рдПрдХ рдЙрджрд╛рд╣рд░рдг рдХреЗ рд░реВрдк рдореЗрдВ, рдПрдХ рд╣реА рд╕реЗрд▓ рдХреЛ рдПрдХ рд╣реА рд╕рдордп рдореЗрдВ рдЫрд╛рдпрд╛рдВрдХрд┐рдд рдФрд░ рд▓реЙрдХ рдирд╣реАрдВ рдХрд┐рдпрд╛ рдЬрд╛ рд╕рдХрддрд╛ рд╣реИ; рдпрджрд┐ рдХреЛрдИ рдСрдкрд░реЗрд╢рди рдРрд╕реА рд╕реНрдерд┐рддрд┐ рдХреЛ рдЬрдиреНрдо рджреЗ рд╕рдХрддрд╛ рд╣реИ, рддреЛ рдпрд╣ Maybe рдореЛрдирдб рдХреЗ рд╕рд╛рде рдЪрд┐рд╣реНрдирд┐рдд рд╣реИ (рдЖрдорддреМрд░ рдкрд░ рдпрд╣ рдЯрд╛рдЗрдк type TransformFunction a = a -> Maybe a ), рдФрд░ рдЕрдЧрд░ рдпрд╣ рдЗрд╕ рд╕реНрдерд┐рддрд┐ рдХреА рдУрд░ рдЬрд╛рддрд╛ рд╣реИ, рддреЛ рдкрд░рд┐рдгрд╛рдо Nothing рд╣реЛрдЧрд╛, рдХреНрдпреЛрдВрдХрд┐ рдХрд╛рд░реНрдпрдХреНрд░рдо рдореЗрдВ рдХреЛрдИ рднреА рд╡рд╕реНрддреБ рдЕрд╕рдВрдЧрдд рд╕реНрдерд┐рддрд┐ рдореЗрдВ рдореМрдЬреВрдж рдирд╣реАрдВ рд╣реЛ рд╕рдХрддреА рд╣реИред рдЪреВрдВрдХрд┐ Nothing , рдмрджрд▓реЗ рдореЗрдВ, рдЕрдиреНрдп рд╡рд╕реНрддреБрдУрдВ рдХрд╛ рдПрдХ рдЕрднрд┐рдиреНрди рд╣рд┐рд╕реНрд╕рд╛ рдирд╣реАрдВ рд╣реЛ рд╕рдХрддрд╛ рд╣реИ, рдкреВрд░реЗ рдХреНрд╖реЗрддреНрд░ рдореЗрдВ рдЕрд╕рдВрдЧрдард┐рдд рд╣реЛ рдЬрд╛рдПрдЧрд╛, рдЬрд┐рд╕рдХрд╛ рдЕрд░реНрде рд╣реЛрдЧрд╛ рд╕рдорд╛рдзрд╛рди рдХреА рдЕрдиреБрдкрд╕реНрдерд┐рддрд┐ред

рдХреНрд╖реИрддрд┐рдЬ рдФрд░ рдКрд░реНрдзреНрд╡рд╛рдзрд░ рд▓рд╛рдЗрдиреЛрдВ рдХреЗ рд╕рд┐рдВрдХреНрд░рдирд╛рдЗрдЬрд╝реЗрд╢рди рджреНрд╡рд╛рд░рд╛ рдХреНрд╖реЗрддреНрд░ рдХреА рд╕реНрдерд┐рд░рддрд╛ рд╕реБрдирд┐рд╢реНрдЪрд┐рдд рдХреА рдЬрд╛рддреА рд╣реИред рдЗрд╕ рдкреНрд░рдХрд╛рд░, рдпрджрд┐ рдХреЛрдИ рдХреЛрд╢рд┐рдХрд╛ рдХрд┐рд╕реА рдХреНрд╖реИрддрд┐рдЬ рдЕрд╡рд╕реНрдерд╛ рдореЗрдВ рдХрд┐рд╕реА рдЕрд╡рд╕реНрдерд╛ (рдЪрд┐рддреНрд░рд┐рдд, рдЕрд╡рд░реБрджреНрдз, рдпрд╛ рд░рд┐рдХреНрдд) рдореЗрдВ рд╣реИ, рддреЛ рд╡рд╣ рдЙрд╕реА рд╕реНрдерд┐рддрд┐ рдореЗрдВ рд╕рдВрдЧрдд рдКрд░реНрдзреНрд╡рд╛рдзрд░ рд░реЗрдЦрд╛ рдореЗрдВ рд╣реИ, рдФрд░ рдЗрд╕рдХреЗ рд╡рд┐рдкрд░реАрддред

 flEnsureConsistency :: TransformFunction Field flEnsureConsistency fl = do let lnsHor = flHorLines fl let lnsVer = flVerLines fl lnsHor' <- zipWithM lnSyncWithLineMask (lmTranspose $ map lnMask lnsVer) lnsHor lnsVer' <- zipWithM lnSyncWithLineMask (lmTranspose $ map lnMask lnsHor) lnsVer return $ Field lnsHor' lnsVer' lnSyncWithLineMask :: LineMask -> TransformFunction Line lnSyncWithLineMask lm ln = do lm' <- lm `snSync` lnMask ln return ln { lnMask = lm' } 

рд╣рдо рдмрд╛рдж рдореЗрдВ рд▓рд╛рдЗрди рдХреА рд╕реНрдерд┐рд░рддрд╛ рдХреЗ рдмрд╛рд░реЗ рдореЗрдВ рдмрд╛рдд рдХрд░реЗрдВрдЧреЗ, рдХреНрдпреЛрдВрдХрд┐ рдпрд╣ рд╕реАрдзреЗ рдирд┐рд░реНрдгрдп рдкреНрд░рдХреНрд░рд┐рдпрд╛ рд╕реЗ рд╕рдВрдмрдВрдзрд┐рдд рд╣реИред

рдмреНрд▓реЙрдХ рдХреА рд╕реНрдерд┐рд░рддрд╛ рдХреЛ рдЧреИрд░-рддреБрдЪреНрдЫ рд░реВрдк рд╕реЗ рдкреНрд░рджрд╛рди рдХрд┐рдпрд╛ рдЬрд╛рддрд╛ рд╣реИ: рдЗрд╕рдХреЗ рд▓рд┐рдП, рдмреНрд▓реЙрдХ рдХреНрд╖реЗрддреНрд░ рд╕реЗ рдЙрди рдирд┐рд░рдВрддрд░ рднрд╛рдЧреЛрдВ рдХреЛ рдмрд╛рд╣рд░ рдХрд░рдирд╛ рдЖрд╡рд╢реНрдпрдХ рд╣реИ рдЬреЛ рдЗрд╕реЗ рд╕рдорд╛рдпреЛрдЬрд┐рдд рдирд╣реАрдВ рдХрд░ рд╕рдХрддреЗ рд╣реИрдВред рдЗрд╕ рдкреНрд░рдХрд╛рд░, рдпрджрд┐ рд╕рдВрдЦреНрдпрд╛ 3 рдФрд░ рдореВрд▓ рдХреНрд╖реЗрддреНрд░ рдХреЗ рд╕рд╛рде рдмреНрд▓реЙрдХ рдХреНрд╖реЗрддреНрд░ рд╕реЗ рдорд╛рд╕реНрдХ рдХреЛ рдмрд╛рд╣рд░ рд░рдЦреЗрдВ (рдЙрджрд╛рд╣рд░рдг рдХреЗ рд▓рд┐рдП, рдЗрд╕ рддрдереНрдп рдХреЗ рдХрд╛рд░рдг рдХрд┐ рдпрд╣ рд╕реЗрд▓ рдЕрд╡рд░реБрджреНрдз рдерд╛), рддреЛ рдЗрд╕ рдСрдкрд░реЗрд╢рди рдХрд╛ рдЕрдВрддрд┐рдо рдкрд░рд┐рдгрд╛рдо рдПрдХ рдХреНрд╖реЗрддреНрд░ рдХреЗ рд╕рд╛рде рдПрдХ рдмреНрд▓реЙрдХ рд╣реЛрдЧрд╛ рд▓реЗрдХрд┐рди рдмрд┐рд▓реНрдХреБрд▓ рдирд╣реАрдВ ред

 blEnsureConsistency :: TransformFunction Block blEnsureConsistency bl = do let bms = filter ((blNumber bl <=) . bmSize) $ bmSplit $ blScopeMask bl guard $ not $ null bms return bl { blScopeMask = bmUnion bms } 

рдорд╛рд╕реНрдХ рдХреЗ рд▓рд┐рдП, рд╕реНрдерд┐рд░рддрд╛ рд╕реНрдкрд╖реНрдЯ рд╣реИ рдФрд░ рдкрд╣рд▓реЗ рд╕реЗ рд╣реА рдКрдкрд░ рд╡рд░реНрдгрд┐рдд рдХрд┐рдпрд╛ рдЧрдпрд╛ рд╣реИ: рдЖрдк рдПрдХ рд╣реА рд╕рдордп рдореЗрдВ рдПрдХ рд╣реА рд╕реЗрд▓ рдХреЛ рдкреЗрдВрдЯ рдФрд░ рдмреНрд▓реЙрдХ рдирд╣реАрдВ рдХрд░ рд╕рдХрддреЗред

 lmEnsureConsistency :: TransformFunction LineMask lmEnsureConsistency lm = do guard $ bmIsEmpty $ lmFilledMask lm `bmAnd` lmBlockedMask lm return lm 

рд░реВрдкрд╛рдВрддрд░рдг

рд░реВрдкрд╛рдВрддрд░рдг рдорд╛рд╕реНрдХ рдФрд░ рдмреНрд▓реЙрдХ рдХрд╛ рд╕рдВрдЪрд╛рд▓рди рдмрд╣реБрдд рд╕реАрдорд┐рдд рд╣реИ, рдХреНрдпреЛрдВрдХрд┐ рдХреЛрд╢рд┐рдХрд╛рдУрдВ рдХреЛ рд╣рд▓ рдХрд░рдиреЗ рдХреА рдкреНрд░рдХреНрд░рд┐рдпрд╛ рдореЗрдВ рдЖрдк рдХреЗрд╡рд▓ рд░рдВрдЧ рднрд░ рд╕рдХрддреЗ рд╣реИрдВ рдФрд░ рдмреНрд▓реЙрдХ рдХрд░ рд╕рдХрддреЗ рд╣реИрдВ (рдЕрдкрдирд╛ рджрд┐рдорд╛рдЧ рдмрджрд▓ рд╕рдХрддреЗ рд╣реИрдВ, рдЗрд░реЗрдЬрд╝рд░ рд▓реЗ рд╕рдХрддреЗ рд╣реИрдВ рдФрд░ рдЗрд╕реЗ рдорд┐рдЯрд╛ рдирд╣реАрдВ рд╕рдХрддреЗ рд╣реИрдВ), рдФрд░ рдмреНрд▓реЙрдХ рдХреНрд╖реЗрддреНрд░ рдХреЛ рдХреЗрд╡рд▓ рд╕рдВрдХреБрдЪрд┐рдд рдХрд┐рдпрд╛ рдЬрд╛ рд╕рдХрддрд╛ рд╣реИред

 lmFill :: BitMask -> TransformFunction LineMask lmFill bm lm = lmEnsureConsistency lm { lmFilledMask = lmFilledMask lm `bmOr` bm } lmBlock :: BitMask -> TransformFunction LineMask lmBlock bm lm = lmEnsureConsistency lm { lmBlockedMask = lmBlockedMask lm `bmOr` bm } blExclude :: BitMask -> TransformFunction Block blExclude bm bl = blEnsureConsistency $ bl { blScopeMask = blScopeMask bl `bmAnd` bmNot bm } blKeep :: BitMask -> TransformFunction Block blKeep bm bl = blEnsureConsistency $ bl { blScopeMask = blScopeMask bl `bmAnd` bm } 

рдирд┐рд░реНрдгрдп


рдирд┐рд░реНрдгрдп рдкреНрд░рдХреНрд░рд┐рдпрд╛ рдХреЛ рдЕрд▓рдЧ-рдЕрд▓рдЧ рд╣рд┐рд╕реНрд╕реЛрдВ рдореЗрдВ рдорд╛рдирд╛ рдЬрд╛рдПрдЧрд╛, рдЬрдм рддрдХ рдХрд┐ рд╡реЗ рдЕрдВрддрддрдГ рдмрдбрд╝реА рддрд╕реНрд╡реАрд░ рдирд╣реАрдВ рдмрдирд╛рддреЗ рд╣реИрдВред

рд▓рд╛рдЗрди рдХреА рд╕рдВрдЧрддрд┐

рд╢реБрд░реВ рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП, рд╣рдо рдирд┐рд░рдВрддрд░рддрд╛ рдкрд░ рдЕрдиреБрднрд╛рдЧ рдореЗрдВ рдЫреЛрдбрд╝реЗ рдЧрдП рдЕрдВрддрд░ рдХреЛ рдмрд╣рд╛рд▓ рдХрд░реЗрдВрдЧреЗ, рдФрд░ рдпрд╣ рдШреЛрд╖рдгрд╛ рдХрд░реЗрдВрдЧреЗ рдХрд┐ рдпрджрд┐ рдЙрд╕рдХреЗ рдирдХрд╛рдм рдХреЛ рдЙрд╕рдХреЗ рдмреНрд▓реЙрдХ рдХреЗ рдЕрдиреБрд╕рд╛рд░ рднрд░рд╛ рдЬрд╛рддрд╛ рд╣реИ, рддреЛ рд░реЗрдЦрд╛ рдХреЛ рд╕рдВрдЧрдд рдорд╛рдирд╛ рдЬрд╛рддрд╛ рд╣реИред рдЗрд╕ рд╡рд╛рдХреНрдпрд╛рдВрд╢ рдХреЗ рдкреАрдЫреЗ рджреЛ рдмрд┐рдВрджреБ рдЫрд┐рдкреЗ рд╣реИрдВред рд╕рдмрд╕реЗ рдкрд╣рд▓реЗ, рдЙрди рдХреЛрд╢рд┐рдХрд╛рдУрдВ рдХреЛ рдЬреЛ рдХреНрд╖реЗрддреНрд░ рдореЗрдВ рдХрд┐рд╕реА рднреА рдмреНрд▓реЙрдХ рдореЗрдВ рдирд╣реАрдВ рдЖрддреЗ рд╣реИрдВ, рдЙрдиреНрд╣реЗрдВ рдЕрд╡рд░реБрджреНрдз рдХрд┐рдпрд╛ рдЬрд╛рдирд╛ рдЪрд╛рд╣рд┐рдП (рдпрджрд┐ рд▓рд╛рдЗрди рдореЗрдВ рдХреЛрдИ рдмреНрд▓реЙрдХ рдирд╣реАрдВ рд╣реИ, рддреЛ, рддрджрдиреБрд╕рд╛рд░, рд╕рднреА рдХреЛрд╢рд┐рдХрд╛рдПрдВ рдРрд╕реА рд╣реИрдВ)ред

 lnUpdateBlocked :: [Block] -> TransformFunction LineMask lnUpdateBlocked [] lm = lmBlock (bmNot $ lmBlockedMask lm) lm lnUpdateBlocked bls lm = lmBlock (bmNot $ bmUnion $ map blScopeMask bls) lm 

рджреВрд╕рд░реЗ, рдкреНрд░рддреНрдпреЗрдХ рдмреНрд▓реЙрдХ рдХреЗ рд▓рд┐рдП, blToFillMask рдлрд╝рдВрдХреНрд╢рди рдХрд╛ рдЙрдкрдпреЛрдЧ рдХрд░рдХреЗ, blToFillMask рдПрдХ рдореБрдЦреМрдЯрд╛ рдкреНрд░рд╛рдкреНрдд blToFillMask рд╕рдХрддреЗ рд╣реИрдВ рдЬрд┐рд╕реЗ рдЖрдкрдХреЛ рдкреЗрдВрдЯ рдХрд░рдиреЗ рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╣реИред рдпрд╣ рджреЛ рдорд╛рд╕реНрдХ рдХрд╛ рдкреНрд░рддрд┐рдЪреНрдЫреЗрджрди рд╣реИ, рдЬрд┐рд╕рдХреЗ рдкрд░рд┐рдгрд╛рдорд╕реНрд╡рд░реВрдк рдпрджрд┐ рдЖрдк рдмреНрд▓реЙрдХ рдХреЛ рдЕрдкрдиреЗ рдХреНрд╖реЗрддреНрд░ рдХреЗ рдмрд╛рдПрдВ рдФрд░ рджрд╛рдПрдВ рд╣рд┐рд╕реНрд╕реЛрдВ рдореЗрдВ "рдбреНрд░рд╛рдЗрд╡" рдХрд░рддреЗ рд╣реИрдВред

 blMinimumLeftMask :: Block -> BitMask blMinimumLeftMask bl = bmLeftIncursion (blNumber bl) (blScopeMask bl) blMinimumRightMask :: Block -> BitMask blMinimumRightMask bl = bmRightIncursion (blNumber bl) (blScopeMask bl) blToFillMask :: Block -> BitMask blToFillMask bl = blMinimumLeftMask bl `bmAnd` blMinimumRightMask bl lnUpdateFilled :: [Block] -> TransformFunction LineMask lnUpdateFilled [] = return lnUpdateFilled bls = lmFill (bmUnion $ map blToFillMask bls) 

(рдиреЛрдЯ: рдпрд╣рд╛рдВ рд╣рдордиреЗ рдЖрдЦрд┐рд░рдХрд╛рд░ bmLeftIncursion рдФрд░ bmRightIncursion рдЙрдкрдпреЛрдЧ рдХрд┐рдпрд╛ рд╣реИред рдХрдбрд╝рд╛рдИ рд╕реЗ рдмреЛрд▓рддреЗ рд╣реБрдП, рдпрджрд┐ рд╡реЗ рдХреЗрд╡рд▓ рдЗрд╕реА рдЙрджреНрджреЗрд╢реНрдп рдХреЗ рд▓рд┐рдП рдЙрдкрдпреЛрдЧ рдХрд┐рдП рдЬрд╛рддреЗ рд╣реИрдВ, рддреЛ рд╣рдо рд╕рдВрднрд╡рддрдГ рд╕рдмрд╕реЗ рдЕрд▓рдЧ рджрд┐рдЦреЗрдВрдЧреЗ, рдЕрд░реНрдерд╛рддреН, рд╣рдо рдмрд┐рдЯ рдорд╛рд╕реНрдХ рдХреЛ рддрдм рддрдХ рднрд░реЗрдВрдЧреЗ рдЬрдм рддрдХ рдХрд┐ рдмрд╣реБрдд рдкрд╣рд▓реЗ рдирд╣реАрдВ рднрд░ рдЬрд╛рддрд╛ред рд╕реНрд░реЛрдд рдорд╛рд╕реНрдХред)

рдЗрд╕ рдкреНрд░рдХрд╛рд░, рдЬреИрд╕рд╛ рдХрд┐ рдкрд╣рд▓реЗ рдЙрд▓реНрд▓реЗрдЦ рдХрд┐рдпрд╛ рдЧрдпрд╛ рд╣реИ, рдПрдХ рдкрдВрдХреНрддрд┐ рдХреЗ рд▓рд┐рдП рд╕реНрдерд┐рд░рддрд╛ рдХреА рд╕реНрдерд┐рддрд┐ рдпрд╣ рд╕реБрдирд┐рд╢реНрдЪрд┐рдд рдХрд░рддреА рд╣реИ рдХрд┐ рдЗрд╕рдХреЗ рд╕рднреА рдмреНрд▓реЙрдХ рдкреВрд░реЗ рд╣реЛрдиреЗ рдкрд░ рдЗрд╕рдХрд╛ рдореБрдЦреМрдЯрд╛ рд╣рдореЗрд╢рд╛ рдкреВрд░рд╛ рд╣реЛ рдЬрд╛рдПрдЧрд╛ред

 lnEnsureConsistency :: TransformFunction Line lnEnsureConsistency ln = do let bls = lnBlocks ln lm <- lnUpdateBlocked bls >=> lnUpdateFilled bls $ lnMask ln return $ ln { lnMask = lm } 

рд╕рд░рд▓ рд░реЗрдЦрд╛ рд░реВрдкрд╛рдВрддрд░рдг

рд▓рд╛рдЗрди рдХреЗ рднреАрддрд░ рдирд┐рд░реНрдгрдп рдЕрдирд┐рд╡рд╛рд░реНрдп рд░реВрдк рд╕реЗ рджреЛ рдкрд░рд┐рд╡рд░реНрддрдиреЛрдВ рдХреЗ рд▓рд┐рдП рдЙрдмрд▓рддрд╛ рд╣реИред

рдкрд╣рд▓рд╛ рдкрд░рд┐рд╡рд░реНрддрди, рд╡рд╛рд╕реНрддрд╡ рдореЗрдВ, рд╕реНрдерд┐рд░рддрд╛ рдХреА рд╕реНрдерд┐рддрд┐ рдХрд╛ рд╡рд┐рд▓реЛрдо рд╣реИ: рдпрд╣ рд╕реБрдирд┐рд╢реНрдЪрд┐рдд рдХрд░рддрд╛ рд╣реИ рдХрд┐ рдпрджрд┐ рдореБрдЦреМрдЯрд╛ рдкреВрд░рд╛ рд╣реЛ рдЧрдпрд╛ рд╣реИ рддреЛ рдмреНрд▓реЙрдХ рдкреВрд░рд╛ рд╣реЛ рдЬрд╛рдПрдЧрд╛ред рдЗрд╕рдХреЗ рд▓рд┐рдП рддреАрди рдХреНрд░рд┐рдпрд╛рдУрдВ рдХрд╛ рдЙрдкрдпреЛрдЧ рдХрд┐рдпрд╛ рдЬрд╛рддрд╛ рд╣реИред

  1. рд╕рднреА рдЕрд╡рд░реБрджреНрдз рдХреЛрд╢рд┐рдХрд╛рдУрдВ рдХреЛ рд╕рднреА рдмреНрд▓реЙрдХреЛрдВ рдХреЗ рдХреНрд╖реЗрддреНрд░реЛрдВ рд╕реЗ рдмрд╛рд╣рд░ рд░рдЦрд╛ рдЬрд╛рдирд╛ рдЪрд╛рд╣рд┐рдПред

     lnRemoveBlocked :: LineMask -> TransformFunction [Block] lnRemoveBlocked = mapM . blExclude . lmBlockedMask 

  2. рдпрджрд┐ рдмреНрд▓реЙрдХ рдореБрдЦреМрдЯрд╛ рдХреЗ рдХрд┐рд╕реА рднреА рдирд┐рд░рдВрддрд░ рдЫрд╛рдпрд╛рдВрдХрд┐рдд рднрд╛рдЧ рдХреЛ рд╕рдорд╛рдпреЛрдЬрд┐рдд рдирд╣реАрдВ рдХрд░ рд╕рдХрддрд╛ рд╣реИ (рдЕрд░реНрдерд╛рдд, рдпрджрд┐ рдпрд╣ рдмреНрд▓реЙрдХ рдХреНрд╖реЗрддреНрд░ рд╕реЗ рдмрд╛рд╣рд░ рдирд┐рдХрд▓рддрд╛ рд╣реИ рдпрд╛ рдЗрд╕рдХреА рд╕рдВрдЦреНрдпрд╛ рд╕реЗ рдмрдбрд╝рд╛ рдЖрдХрд╛рд░ рд╣реИ), рддреЛ рдЗрд╕реЗ рдмреНрд▓реЙрдХ рдХреНрд╖реЗрддреНрд░ рд╕реЗ рдмрд╛рд╣рд░ рд░рдЦрд╛ рдЬрд╛рдирд╛ рдЪрд╛рд╣рд┐рдПред

     lnRemoveFilled :: LineMask -> TransformFunction [Block] lnRemoveFilled lm = mapM (\ bl -> foldM f bl $ bmSplit $ lmFilledMask lm) where f bl bm = if blCanContainMask bm bl then return bl else blExclude (bmExpand bm) bl blCanContainMask :: BitMask -> Block -> Bool blCanContainMask bm bl = let bm' = bmFillGaps bm in bmSize bm' <= blNumber bl && bmIsEmpty (bm' `bmAnd` bmNot (blScopeMask bl)) 

  3. рдЕрдкрдиреЗ рдмрд╛рдПрдВ рдкрдбрд╝реЛрд╕реА рдХреЗ blMinimumRightMask рджрд╛рд╣рд┐рдиреЗ рдкрдбрд╝реЛрд╕реА рдХреЗ blMinimumRightMask рдкреНрд░рддреНрдпреЗрдХ рдмреНрд▓реЙрдХ рдХреЗ рдХреНрд╖реЗрддреНрд░ рд╕реЗ рдмрд╛рд╣рд░ рд░рдЦрд╛ рдЬрд╛рдирд╛ рдЪрд╛рд╣рд┐рдП (рдпрд╣рд╛рдВ рдЙрдиреНрд╣реЗрдВ рдКрдкрд░ рд╡рд░реНрдгрд┐рдд рд░реВрдк рдореЗрдВ рдмрд┐рд▓реНрдХреБрд▓ рдЖрд╡рд╢реНрдпрдХрддрд╛ рд╣реИ)ред рд╕рдЯреАрдХ рд╣реЛрдиреЗ рдХреЗ рд▓рд┐рдП, рдПрдХ рд╕реЗрд▓ рджреНрд╡рд╛рд░рд╛ рд╡рд┐рд╕реНрддрд╛рд░рд┐рдд рдЗрди рдорд╛рд╕реНрдХ рдХреЛ рдмрд╛рд╣рд░ рд░рдЦрд╛ рдЧрдпрд╛ рд╣реИ, рдХреНрдпреЛрдВрдХрд┐ рдмреНрд▓реЙрдХ рдХреЗ рдмреАрдЪ рдХрдо рд╕реЗ рдХрдо рдПрдХ рдЦрд╛рд▓реА рд╕реЗрд▓ рд╣реЛрдирд╛ рдЪрд╛рд╣рд┐рдПред

     lnExcludeNeighbours :: TransformFunction [Block] lnExcludeNeighbours bls = sequence $ scanr1 (flip $ wrap $ blExclude . bmExpand . blMinimumRightMask) $ scanl1 (wrap $ blExclude . bmExpand . blMinimumLeftMask) $ map return bls 

рд╕рд╛рде рдореЗрдВ, рдпреЗ рдХреНрд░рд┐рдпрд╛рдПрдВ рдирд┐рдореНрдирд▓рд┐рдЦрд┐рдд рдлрд╝рдВрдХреНрд╢рди рдХрд╛ рдирд┐рд░реНрдорд╛рдг рдХрд░рддреА рд╣реИрдВ (рдмрд╛рдж рдореЗрдВ slLoop рдлрд╝рдВрдХреНрд╢рди рдХрд╛ рд╡рд░реНрдгрди рдХрд┐рдпрд╛ рдЬрд╛рдПрдЧрд╛):

 lnSimpleTransform :: TransformFunction Line lnSimpleTransform ln = do let lm = lnMask ln bls <- lnRemoveBlocked lm >=> slLoop (lnRemoveFilled lm >=> lnExcludeNeighbours) $ lnBlocks ln lnEnsureConsistency ln { lnBlocks = bls } 

рджреВрд╕рд░реА рдкрдВрдХреНрддрд┐ рд░реВрдкрд╛рдВрддрд░рдг

рдпрджрд┐ рд╣рдо рд╕рднреА рдмреНрд▓реЙрдХреЛрдВ рдореЗрдВ рд╕реЗ рд╕рдмрд╕реЗ рдмрд╛рдИрдВ рдУрд░ рд▓реЗ рдЬрд╛рддреЗ рд╣реИрдВ, рдЬрд┐рд╕рдореЗрдВ рд╕рд┐рджреНрдзрд╛рдВрдд рд░реВрдк рдореЗрдВ рдорд╛рд╕реНрдХ рдХрд╛ рдХреБрдЫ рдЫрд╛рдпрд╛рдВрдХрд┐рдд рд╣рд┐рд╕реНрд╕рд╛ рд╣реЛ рд╕рдХрддрд╛ рд╣реИ, рддреЛ рдЗрд╕рдХреА рд╕рд╣реА рд╕реНрдерд┐рддрд┐ рдЗрд╕ рдорд╛рд╕реНрдХ рддрдХ рд╣реА рд╕реАрдорд┐рдд рд╣реЛрдЧреА, рдХреНрдпреЛрдВрдХрд┐ рдпрджрд┐ рдпрд╣ рдЕрдзрд┐рдХ рджрд╛рдИрдВ рдУрд░ рдЪрд▓рд╛ рдЬрд╛рддрд╛ рд╣реИ, рддреЛ рдпрд╣ рдЫрд╛рдпрд╛рдВрдХрд┐рдд рдХреНрд╖реЗрддреНрд░ рдЕрдм рдХрд┐рд╕реА рдХреЛ рднреА рдирд╣реАрдВ рджрд┐рдпрд╛ рдЬрд╛рдПрдЧрд╛ред рдЗрди рдмреНрд▓реЙрдХреЛрдВ рдХреЗ рд╕рд╣реА рд╣реЛрдиреЗ рдХреЗ рд▓рд┐рдП рд╕рдорд╛рди рд╡рд┐рдЪрд╛рд░ рд╕рд╣реА рд╣реИрдВред

 lnExtremeOwners :: BitMask -> TransformFunction [Block] lnExtremeOwners bm bls = do bls' <- fmap reverse $ maybe (return bls) (f bmLeftIncursion bls) (h bls) fmap reverse $ maybe (return bls') (f bmRightIncursion bls') (h bls') where fg = varyNth (\ bl -> blKeep (g (blNumber bl) bm) bl) h = findIndex (blCanContainMask bm) varyNth :: Monad m => (a -> ma) -> [a] -> Int -> m [a] varyNth f xs idx = do let (xs1, x : xs2) = splitAt idx xs x' <- fx return $ xs1 ++ x' : xs2 

рдорд╛рд╕реНрдХрд┐рдВрдЧ рдХреЗ рдкреНрд░рддреНрдпреЗрдХ рдирд┐рд░рдВрддрд░ рднрд╛рдЧ рдореЗрдВ рдЗрд╕ рддрд░реНрдХ рдХреЛ рд▓рд╛рдЧреВ рдХрд░рддреЗ рд╣реБрдП, рд╣рдо рджреВрд╕рд░реА рдкрдВрдХреНрддрд┐ рдкрд░рд┐рд╡рд░реНрддрди рдкреНрд░рд╛рдкреНрдд рдХрд░рддреЗ рд╣реИрдВ:

 lnTransformByExtremeOwners :: TransformFunction Line lnTransformByExtremeOwners ln = do bls <- foldM (flip lnExtremeOwners) (lnBlocks ln) $ bmSplit $ lmFilledMask $ lnMask ln lnEnsureConsistency ln { lnBlocks = bls } 

рдХреНрд╖реЗрддреНрд░ рд░реВрдкрд╛рдВрддрд░рдг

рдлрд╝реАрд▓реНрдб рдХрд╛ рдЕрдкрдирд╛ рдХреЛрдИ рд╡рд┐рд╢реЗрд╖ рдкрд░рд┐рд╡рд░реНрддрди рдирд╣реАрдВ рд╣реИ, рдЗрд╕рдХреЗ рд▓рд┐рдП рдПрдХрдорд╛рддреНрд░ рд╡рд┐рдХрд▓реНрдк рдХреБрдЫ рддреИрдпрд╛рд░ рдХрд┐рдП рдЧрдП рдкрд░рд┐рд╡рд░реНрддрди рд▓реЗрдирд╛ рд╣реИ рдФрд░ рдЗрд╕реЗ рд╕рднреА рд▓рд╛рдЗрдиреЛрдВ рдкрд░ рд▓рд╛рдЧреВ рдХрд░рдирд╛ рд╣реИред

 flTransformByLines :: TransformFunction Line -> TransformFunction Field flTransformByLines f fl = do lnsHor <- mapM f (flHorLines fl) fl' <- flEnsureConsistency fl { flHorLines = lnsHor } lnsVer <- mapM f (flVerLines fl') flEnsureConsistency fl' { flVerLines = lnsVer } 

рд╢рд╛рдЦрд╛рдУрдВ рдореЗрдВ

рдЪреВрдВрдХрд┐ рдЬрд╛рдкрд╛рдиреА рдХреНрд░реЙрд╕рд╡рд░реНрдб рдХреЛ рд╣рд▓ рдХрд░рдирд╛ рдПрдХ рдПрдирдкреА-рдкреВрд░реНрдг рдХрд╛рд░реНрдп рд╣реИ, рдЗрд╕рд▓рд┐рдП рдЖрдк рдмрд┐рдирд╛ рдмреНрд░рд╛рдВрдЪрд┐рдВрдЧ рдХреЗ рдирд╣реАрдВ рдХрд░ рдкрд╛рдПрдВрдЧреЗред рд╣рдо рд╢рд╛рдЦрд╛рдУрдВ рдХреЗ рдкреНрд░рдХрд╛рд░ рдХреЗ рдПрдХ рдлрд╝рдВрдХреНрд╢рди рдХреЗ рд░реВрдк рдореЗрдВ рдмреНрд░рд╛рдВрдЪрд┐рдВрдЧ рдХреЛ рдкрд░рд┐рднрд╛рд╖рд┐рдд рдХрд░реЗрдВрдЧреЗ type ForkFunction a = a -> [[a]] , рдЬрд╣рд╛рдВ рдЖрдВрддрд░рд┐рдХ рд╕реВрдЪреА рдореЗрдВ рдкрд╛рд░рд╕реНрдкрд░рд┐рдХ рд░реВрдк рд╕реЗ рдЕрдирдиреНрдп рд╡рд┐рдХрд▓реНрдк рдФрд░ рдмрд╛рд╣рд░реА рдПрдХ - рдЗрди рд╡рд┐рдХрд▓реНрдкреЛрдВ рдХрд╛ рдЙрддреНрдкрд╛рджрди рдХрд░рдиреЗ рдХреЗ рд╡рд┐рднрд┐рдиреНрди рддрд░реАрдХреЗ рд╢рд╛рдорд┐рд▓ рд╣реИрдВред

рд╕рдмрд╕реЗ рд╕рд░рд▓ рддрд░реАрдХрд╛ рдХреЛрд╢рд┐рдХрд╛рдУрдВ рдореЗрдВ рд╢рд╛рдЦрд╛рдУрдВ рдореЗрдВ рдмрдВрдЯ рд░рд╣рд╛ рд╣реИ: рдкреНрд░рддреНрдпреЗрдХ рдЦрд╛рд▓реА рд╕реЗрд▓ рдмрд╛рд╣рд░реА рд╕реВрдЪреА рдХреЗ рдПрдХ рддрддреНрд╡ рдХреЛ рдЙрддреНрдкрдиреНрди рдХрд░рддрд╛ рд╣реИ, рдЬреЛ рдмрджрд▓реЗ рдореЗрдВ рджреЛ рддрддреНрд╡реЛрдВ рдХреА рдПрдХ рд╕реВрдЪреА рд╣реИ, рдЬрд┐рд╕рдореЗрдВ рд╕реЗ рдПрдХ рдореЗрдВ рдпрд╣ рд╕реЗрд▓ рднрд░ рдЬрд╛рддрд╛ рд╣реИ рдФрд░ рджреВрд╕рд░реЗ рдореЗрдВ рдЕрд╡рд░реБрджреНрдз рд╣реЛрддрд╛ рд╣реИред

 lnForkByCells :: ForkFunction Line lnForkByCells ln = do let lm = lnMask ln bm <- bmByOne $ lmEmptyMask lm return $ do lm' <- [fromJust $ lmBlock bm lm, fromJust $ lmFill bm lm] maybeToList $ lnEnsureConsistency ln { lnMask = lm' } flForkByCells :: ForkFunction Field flForkByCells fl = do let lnsHor = flHorLines fl let lnsVer = flVerLines fl idx <- findIndices (not . clIsCompleted) lnsHor let (lns1, ln : lns2) = splitAt idx lnsHor lns <- lnForkByCells ln return $ do ln' <- lns maybeToList $ flEnsureConsistency $ Field (lns1 ++ ln' : lns2) lnsVer 

рд▓рд╛рдЗрди рдХреЗ рд▓рд┐рдП рдПрдХ рдФрд░ рдмреНрд░рд╛рдВрдЪрд┐рдВрдЧ рд╡рд┐рдзрд┐ рднреА рдЙрдкрд▓рдмреНрдз рд╣реИ: рдорд╛рд╕реНрдХ (рдмрд╛рд╣рд░реА рд╕реВрдЪреА) рдХреЗ рдкреНрд░рддреНрдпреЗрдХ рдирд┐рд░рдВрддрд░ рдЫрд╛рдпрд╛рдВрдХрд┐рдд рднрд╛рдЧ рдХреЗ рд▓рд┐рдП, рдЖрдк рдЙрди рдмреНрд▓реЙрдХреЛрдВ рдХрд╛ рдПрдХ рд╕реЗрдЯ рдкрд░ рд╡рд┐рдЪрд╛рд░ рдХрд░ рд╕рдХрддреЗ рд╣реИрдВ рдЬрд┐рдирдореЗрдВ рдЗрд╕реЗ (рдЖрдВрддрд░рд┐рдХ рд╕реВрдЪреА) рд╣реЛ рд╕рдХрддрд╛ рд╣реИ, рдЬреЛ рд╡рд┐рдХрд▓реНрдк рд╢рд╛рдЦрд╛рдУрдВ рдХреЛ рдкрд░рд┐рднрд╛рд╖рд┐рдд рдХрд░рддреЗ рд╣реИрдВред

 lnForkByOwners :: ForkFunction Line lnForkByOwners ln = do let bls = lnBlocks ln bm <- bmSplit $ lmFilledMask $ lnMask ln case findIndices (blCanContainMask bm) bls of [_] -> [] idxs -> return $ do idx <- idxs maybeToList $ do bls' <- varyNth (g bm) bls idx lnEnsureConsistency ln { lnBlocks = bls' } where g bm bl = blKeep ((bmAnd `on` ($ bm) . ($ blNumber bl)) bmLeftIncursion bmRightIncursion) bl 

рд╕рд╛рдорд╛рдиреНрдпреАрдХреГрдд рдХрд╛рд░реНрдп

рдпрд╣ рдкрд░рд┐рд╡рд░реНрддрди рдХреЗ рдЕрдзрд┐рдХрд╛рдВрд╢ рдкрд░рд┐рд╡рд░реНрддрдиреЛрдВ рдХреЛ рд▓рд╛рдЧреВ рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП рд╕рдордЭ рдореЗрдВ рдЖрддрд╛ рд╣реИред рдЗрд╕ рдорд╛рдорд▓реЗ рдореЗрдВ, рдЖрдк рдХреЗрд╡рд▓ рддрдм рддрдХ рдкрд░рд┐рд╡рд░реНрддрди рд▓рд╛рдЧреВ рдХрд░ рд╕рдХрддреЗ рд╣реИрдВ рдЬрдм рддрдХ рдХрд┐ рдпрд╣ рдХрдо рд╕реЗ рдХрдо рдХреБрдЫ рдирд╣реАрдВ рдмрджрд▓рддрд╛ рд╣реИ, рдпрд╛ рдЖрдк (рдЙрд╕ рд╕реНрдерд┐рддрд┐ рдореЗрдВ рдЬрдм рдЕрдирд╛рд╡рд╢реНрдпрдХ рдЖрд╡реЗрджрди рдореЗрдВ рдХрд╛рдлреА рд╕рдордп рд▓рдЧ рд╕рдХрддрд╛ рд╣реИ) рдкреВрд░реНрдгрддрд╛ рдХреЗ рд▓рд┐рдП рд╡рд╕реНрддреБ рдХреА рдкреВрд░реНрд╡ рдЬрд╛рдВрдЪ рдХрд░реЗрдВред

 slLoop :: Eq a => TransformFunction a -> TransformFunction a slLoop fx = do x' <- fx if x == x' then return x else slLoop fx' slSmartLoop :: (Completable a, Eq a) => TransformFunction a -> TransformFunction a slSmartLoop fx | clIsCompleted x = return x | otherwise = do x' <- fx if x == x' then return x else slLoop fx' 

рд╡рд┐рд╢реЗрд╖ рдбреЗрдЯрд╛ рдкреНрд░рдХрд╛рд░ рдФрд░ рдмреНрд░рд╛рдВрдЪрд┐рдВрдЧ рд╡рд┐рдзрд┐ рдХреА рдкрд░рд╡рд╛рд╣ рдХрд┐рдП рдмрд┐рдирд╛ рдмреНрд░рд╛рдВрдЪрд┐рдВрдЧ рдкрд░рд┐рдгрд╛рдореЛрдВ рдХреЛ рд╕рдВрд╕рд╛рдзрд┐рдд рдХрд┐рдпрд╛ рдЬрд╛ рд╕рдХрддрд╛ рд╣реИред рдРрд╕рд╛ рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП, рдПрдХ рдирд┐рд╢реНрдЪрд┐рдд рд╢рд╛рдЦрд╛ рдкрджреНрдзрддрд┐ рдХреЛ рд▓рд╛рдЧреВ рдХрд░рдирд╛, рдФрд░ рдлрд┐рд░ рдкреНрд░рддреНрдпреЗрдХ рдкрд░рд┐рдгрд╛рдореА рд╡рд╕реНрддреБ рдореЗрдВ рдХреБрдЫ рдкрд░рд┐рд╡рд░реНрддрди рд▓рд╛рдЧреВ рдХрд░рдирд╛, рдкрд╛рд░рд╕реНрдкрд░рд┐рдХ рд░реВрдк рд╕реЗ рдЕрдирдиреНрдп рд╢рд╛рдЦрд╛рдУрдВ рдХреЗ рдкреНрд░рддреНрдпреЗрдХ рд╕реЗрдЯ рдХреЗ рд▓рд┐рдП рдФрд╕рдд рдореВрд▓реНрдп рд▓реЗрдирд╛ рдЖрд╡рд╢реНрдпрдХ рд╣реИ, рдФрд░ рдлрд┐рд░ рд╡рд┐рднрд┐рдиреНрди рд╢рд╛рдЦрд╛ рдмрд┐рдВрджреБрдУрдВ рджреНрд╡рд╛рд░рд╛ рдкреНрд░рд╛рдкреНрдд рдЗрди рдФрд╕рдд рд╡рд╕реНрддреБрдУрдВ рдХреЛ рд╕рд┐рдВрдХреНрд░рдирд╛рдЗрдЬрд╝ рдХрд░реЗрдВред рдореИрдВ рдЗрд╕рдХрд╛ рд╡рд┐рд╕реНрддрд╛рд░ рд╕реЗ рд╡рд░реНрдгрди рдирд╣реАрдВ рдХрд░реВрдВрдЧрд╛, рд▓реЗрдХрд┐рди рдЗрд╕ рдСрдкрд░реЗрд╢рди рдХреЗ рд▓рд┐рдП рдкреВрд░реНрдгрддрд╛ рдХреЗ рд▓рд┐рдП рдЬрд╛рдБрдЪ рд╕реЗ рд╕рдВрдмрдВрдзрд┐рдд рдПрдХ рдЕрдиреБрдХреВрд▓рд┐рдд рд╕рдВрд╕реНрдХрд░рдг рднреА рдЙрдкрд▓рдмреНрдз рд╣реИред

 slForkAndSyncAll :: (Syncable a) => ForkFunction a -> TransformFunction a -> TransformFunction a slForkAndSyncAll fgx = do xs <- mapM (snAverageAll . mapMaybe g) $ fx snSyncAll (x : xs) slForkAndSmartSync :: (Syncable a, Completable a, Eq a) => ForkFunction a -> TransformFunction a -> TransformFunction a slForkAndSmartSync fgx = foldr h (return x) (fx) where h xs mx = do x' <- mx if clIsCompleted x' then mx else case mapMaybe (snSync x') xs of [] -> Nothing xs' -> case filter (/= x') xs' of [] -> return x' xs'' -> snAverageAll . mapMaybe g $ xs'' 

рдЕрдВрдд рдореЗрдВ, рдпрджрд┐ рдЕрдиреНрдп рд╕рднреА рд╡рд┐рдлрд▓ рд╣реЛ рдЬрд╛рддреЗ рд╣реИрдВ, рддреЛ рдЖрдк рдкреБрдирд░рд╛рд╡реГрддреНрддрд┐ рдореЗрдВ рдЬрд╛ рд╕рдХрддреЗ рд╣реИрдВред рдХреЗрд╡рд▓ рдЗрд╕ рддрд░рд╣ рд╕реЗ рдЖрдк рд╕рднреА рд╕рдорд╛рдзрд╛рди рдкреНрд░рд╛рдкреНрдд рдХрд░ рд╕рдХрддреЗ рд╣реИрдВ, рдЕрдЧрд░ рдХрдИ рд╣реИрдВред

 slAllSolutions :: (Completable a) => ForkFunction a -> TransformFunction a -> a -> [a] slAllSolutions fgx = do x' <- maybeToList $ gx if clIsCompleted x' then return x' else case fx' of (xs : _) -> do x'' <- xs slAllSolutions fg x'' [] -> [] 

рдлрд┐рди рд╡реЗрдВрдХреЛ

рд╡рд╣ рд╕рдм рд╣реИред рдЙрдкрд▓рдмреНрдз рдЙрдкрдХрд░рдг рдХреБрдЫ рд╕рд░рд▓ рдЪрд░рдгреЛрдВ рдореЗрдВ рд╕реЙрд▓реНрд╡рд░ рдкреНрд░рд╛рдкреНрдд рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП рдкрд░реНрдпрд╛рдкреНрдд рд╣реИрдВред

  1. рджреЛ рд▓рд╛рдЗрди рдЯреНрд░рд╛рдВрд╕рдлреЙрд░реНрдо рдХреЛ рдорд┐рд▓рд╛рдПрдВред

     lineTransform = slSmartLoop $ lnSimpleTransform >=> lnTransformByExtremeOwners 

  2. рд╣рдо рд▓рд╛рдЗрди-рд╡рд┐рд╢рд┐рд╖реНрдЯ рдмреНрд░рд╛рдВрдЪрд┐рдВрдЧ рдХреА рдкреНрд░рдХреНрд░рд┐рдпрд╛ рдХрд░рддреЗ рд╣реИрдВред

     lineTransform' = slForkAndSyncAll lnForkByOwners lineTransform 

  3. рд╣рдо рдЗрди рджреЛ рдкрд░рд┐рд╡рд░реНрддрдиреЛрдВ рд╕реЗ рдПрдХ рдХреНрд╖реЗрддреНрд░ рдкрд░рд┐рд╡рд░реНрддрди рдХреА рд░рдЪрдирд╛ рдХрд░рддреЗ рд╣реИрдВред

     fieldTransform = slSmartLoop $ slSmartLoop (flTransformByLines lineTransform) >=> flTransformByLines lineTransform' 

  4. рд╣рдо рдХреНрд╖реЗрддреНрд░ рдХреЛ рдХреЛрд╢рд┐рдХрд╛рдУрдВ рдореЗрдВ рд╡рд┐рднрд╛рдЬрд┐рдд рдХрд░рдиреЗ рдХреЗ рдкрд░рд┐рдгрд╛рдореЛрдВ рдХреЛ рд╕рдВрд╕рд╛рдзрд┐рдд рдХрд░рддреЗ рд╣реИрдВред

     fieldTransform' = slForkAndSmartSync flForkByCells fieldTransform 

  5. рдкрд┐рдЫрд▓реЗ рджреЛ рдкрд░рд┐рд╡рд░реНрддрдиреЛрдВ рдХреЛ рдорд┐рд▓рд╛рдПрдВред

     fieldTransform'' = slSmartLoop $ fieldTransform >=> fieldTransform' 

  6. рдФрд░ рдЕрдВрдд рдореЗрдВ, рдкреБрдирд░рд╛рд╡реГрддреНрддрд┐ рдЬреЛрдбрд╝реЗрдВред

     solve = slAllSolutions flForkByCells fieldTransform'' 

рдЕрдВрддрднрд╛рд╖рдг


рдпрд╣ рдХрд╛рд░реНрдпрдХреНрд░рдо рдЙрди рд╕рднреА рдХреНрд░реЙрд╕рд╡рд░реНрдбреЛрдВ рдкрд░ рдмрд╣реБрдд рддреЗрдЬрд╝реА рд╕реЗ рдЪрд▓рддрд╛ рд╣реИ рдЬрд┐рдирдХреЗ рдкрд╛рд╕ рдПрдХ рд╣реА рд╕рдорд╛рдзрд╛рди рд╣реИ: рдореЗрд░реЗ рд▓реИрдкрдЯреЙрдк рдкрд░ рдореМрдЬреВрдж рд╣рдЬрд╛рд░реЛрдВ рдХреНрд░реЙрд╕рд╡рд░реНрдб рдореЗрдВ рд╕реЗ рдХреЗрд╡рд▓ рджреЛ (рдкреНрд░рд╕реНрддрд╛рд╡рдирд╛ рдореЗрдВ рдмрдирд╛рдпрд╛ рдЧрдпрд╛ рдПрдХ рд╕рд╣рд┐рдд) рдПрдХ рдорд┐рдирдЯ рд╕реЗ рдЕрдзрд┐рдХ рд╕рдордп рддрдХ рд╣рд▓ рдХрд┐рдпрд╛ рдЬрд╛рддрд╛ рд╣реИ, рд▓рдЧрднрдЧ рд╕рднреА 10 рд╕реЗрдХрдВрдб рдореЗрдВ рдлрд┐рдЯ рд╣реЛрддреЗ рд╣реИрдВ, рдФрд░ рдЙрдирдореЗрдВ рд╕реЗ рдХрд┐рд╕реА рдХреЛ рднреА рдкреБрдирд░рд╛рд╡реГрддреНрддрд┐ рдХреА рдЖрд╡рд╢реНрдпрдХрддрд╛ рдирд╣реАрдВ рд╣реЛрддреА рд╣реИред

рд╕реИрджреНрдзрд╛рдВрддрд┐рдХ рд░реВрдк рд╕реЗ, рдХреБрдЫ рдкрд░рд┐рд╢реЛрдзрди рдХреЗ рд╕рд╛рде, рдХрд╛рд░реНрдпрдХреНрд░рдо рдХрд╛ рдЙрдкрдпреЛрдЧ рд╕реНрд╡рдЪрд╛рд▓рд┐рдд рд░реВрдк рд╕реЗ рдХреНрд░реЙрд╕рд╡рд░реНрдб рдХреА рдЬрдЯрд┐рд▓рддрд╛ рдХрд╛ рдЖрдХрд▓рди рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП рдХрд┐рдпрд╛ рдЬрд╛ рд╕рдХрддрд╛ рд╣реИ (рдХреНрдпреЛрдВрдХрд┐ рд╕рдорд╛рдзрд╛рди рд╡рд┐рдзрд┐рдпрд╛рдВ рдЖрдо рддреМрд░ рдкрд░ рдХрд┐рд╕реА рд╡реНрдпрдХреНрддрд┐ рджреНрд╡рд╛рд░рд╛ рдЙрдкрдпреЛрдЧ рдХрд┐рдП рдЬрд╛рдиреЗ рдХреЗ рд╕рдорд╛рди рд╣реЛрддреА рд╣реИрдВ) рдФрд░ рд╕рдорд╛рдзрд╛рди рдХреА рд╡рд┐рд╢рд┐рд╖реНрдЯрддрд╛ рдХреЛ рд╕рд╛рдмрд┐рдд рдХрд░рдиреЗ рдХреЗ рд▓рд┐рдП; LaTeX рдХреЛ рдирд┐рд░реНрдпрд╛рдд рдЙрдкрд▓рдмреНрдз рд╣реИ, рдФрд░ рдЬрд▓реНрдж рд╣реА SVN рдореЗрдВ рднреА рджрд┐рдЦрд╛рдИ рджреЗ рд╕рдХрддрд╛ рд╣реИред рдЗрд╕рд▓рд┐рдП, рдпрджрд┐ рдЖрдк рдЪрд╛рд╣реЗрдВ, рддреЛ рдЖрдк рдкрддреНрд░рд┐рдХрд╛рдУрдВ рдХрд╛ рдПрдХ рд╣реЛрдо рдЗрд╢реНрдпреВ рдЖрдпреЛрдЬрд┐рдд рдХрд░ рд╕рдХрддреЗ рд╣реИрдВ :)

Source: https://habr.com/ru/post/In151819/


All Articles