Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- import Control.Applicative
- import Control.Monad
- import Data.List
- import Debug.Trace
- road :: [Int] -> (Int, Int, Int)
- road x = (x !! 0, x !! 1, x !! 2)
- city :: [Int] -> (Int, Int)
- city x = (x !! 0, x !! 1)
- first :: (a, b, c) -> a
- first (a, _, _) = a
- second :: (a, b, c) -> b
- second (_, b, _) = b
- third :: (a, b, c) -> c
- third (_, _, c) = c
- -------------------------------------------------------------------------------
- --- (道路, 国民, 都市, 途中結果)
- func :: [(Int, Int, Int)] -> [(Int, Int, Int)] -> [(Int, Int)] -> [(Int, Int)] -> [(Int, Int)]
- func roads people cities result = if null people then result else func invalidRoads (tail people) integratedCities refreshResult
- where
- man = head people
- tolerance = third man
- validRoads = foldr apply [] roads
- where apply road xs = if third road > tolerance then road : xs else []
- invalidRoads = tailLoop roads $ length validRoads
- integratedCities = integrate cities validRoads
- tailLoop roads num = if num == 0 then roads else tailLoop (tail roads) $ num - 1
- integrate c r = if null r then c else integrate (map (\city -> if (fst city) == (second (head r)) then (fst city, upstream (fst city) c) else city) c) $ (tail r)
- upstream index c = if (fst (c !! index)) == (snd (c !! index)) then index else upstream (snd (c !! index)) c
- possibleCitiesCount = length $ filter (\x -> (snd x) == (upstream (second man) integratedCities)) integratedCities
- refreshResult = map (\x -> if (fst x) == (first man) then (fst x, possibleCitiesCount) else x) $ traceShow result $ result
- main :: IO ()
- main = do
- --- (#都市, #道路)
- [n, m] <- map read . words <$> getLine :: IO [Int]
- --- 道路: (都市s, 都市t, 年)
- roads <- replicateM m $ road . map read . words <$> getLine
- --- #国民
- q <- readLn
- --- 国民: (都市, 年)
- people <- replicateM q $ city . map read . words <$> getLine
- --- 国民に番号を振る
- let indexedPeople = map (\x -> (fst x, (fst (snd x)), (snd (snd x)))) $ zip [1..] people
- --- ソースが若い順にソート
- let sortedRoads = sortBy (\x y -> compare (second x) (second y)) roads
- --- 道路が若い順にソート
- let sortedPeople = sortBy (\x y -> compare (third y) (third x)) indexedPeople
- --- index順に出力
- sequence $ map (\x -> putStrLn $ show $ snd x) $ sortBy (\x y -> compare (fst x) (fst y)) $ func sortedRoads sortedPeople (zip [1..] (take n (iterate (1 +) 1))) $ zip [1..] $ replicate q 0
- return ()
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement