ac-library-hs-1.1.0.0: test/Tests/Scc.hs
module Tests.Scc (tests) where
import AtCoder.Scc qualified as Scc
import Data.Vector qualified as V
import Data.Vector.Unboxed qualified as VU
import System.IO.Unsafe (unsafePerformIO)
import Test.Hspec
import Test.Tasty
import Test.Tasty.HUnit
import Test.Tasty.Hspec
unit_empty :: TestTree
unit_empty = testCase "empty" $ do
graph0 <- Scc.new 0
(@?= V.empty) =<< Scc.scc graph0
pure ()
-- assign
unit_simple :: TestTree
unit_simple = testCase "simple" $ do
graph <- Scc.new 2
Scc.addEdge graph 0 1
Scc.addEdge graph 1 0
scc <- Scc.scc graph
V.length scc @?= 1
unit_selfLoop :: TestTree
unit_selfLoop = testCase "selfLoop" $ do
graph <- Scc.new 2
Scc.addEdge graph 0 0
Scc.addEdge graph 0 0
Scc.addEdge graph 1 1
scc <- Scc.scc graph
V.length scc @?= 2
spec_invalid :: IO TestTree
spec_invalid = testSpec "invalid" $ do
g <- runIO $ Scc.new 2
it "throws error" $ do
Scc.addEdge g 0 10 `shouldThrow` anyException
-- Tests after this line are not in the original ac-library
unit_order :: TestTree
unit_order = testCase "order" $ do
graph <- Scc.new 4
Scc.addEdge graph 0 1
Scc.addEdge graph 1 2
Scc.addEdge graph 2 3
Scc.addEdge graph 3 0
scc <- Scc.scc graph
scc @?= V.singleton (VU.fromList [0, 1, 2, 3])
unit_sccOrder :: TestTree
unit_sccOrder = testCase "sccOrder" $ do
graph <- Scc.new 4
Scc.addEdge graph 0 1
Scc.addEdge graph 1 0
Scc.addEdge graph 2 1
Scc.addEdge graph 3 2
scc <- Scc.scc graph
-- The SCCs are topologically sorted
scc @?= V.fromList [VU.singleton 3, VU.singleton 2, VU.fromList [0, 1]]
unit_multipleSelfLoops :: TestTree
unit_multipleSelfLoops = testCase "multipleSelfLoops" $ do
graph <- Scc.new 2
Scc.addEdge graph 1 0
Scc.addEdge graph 1 1
Scc.addEdge graph 0 0
Scc.addEdge graph 0 0
Scc.addEdge graph 0 0
Scc.addEdge graph 0 0
scc <- Scc.scc graph
scc @?= V.fromList [VU.singleton 1, VU.singleton 0]
tests :: [TestTree]
tests =
[ unit_empty,
unit_simple,
unit_selfLoop,
unsafePerformIO spec_invalid,
unit_order,
unit_sccOrder,
unit_multipleSelfLoops
]