tate (Set a)] -> [D.State (Set a)] -> [DFARule a b]
genDFARule'' rs acc visitedStates tmpStates
  | L.null newTmpStates = acc ++ generatedRules
  | otherwise = genDFARule'' rs (generatedRules ++ acc) (visitedStates ++ newTmpStates) newTmpStates
  where
    generatedRules :: [DFARule a b]
    generatedRules = concat $ L.map (\x -> genDFARule' x rs) tmpStates
    newTmpStates = L.filter (\x -> not (elem x visitedStates)) $ L.map (\(D.Rule _ _ x) -> x) generatedRules

genDFA :: forall a b. (Ord a) => EpsilonNFA a b -> D.DFA (Set a) b
genDFA en
genDFARule'' :: forall a b. (Ord a) => [ENFARule a b] -> [DFARule a b] -> [D.State (Set a)] -> [D.State (Set a)] -> [DFARule a b]
genDFARule'' rs acc visitedStates tmpStates
  | L.null newTmpStates = acc ++ generatedRules
  | otherwise = genDFARule'' rs (generatedRules ++ acc) (visitedStates ++ newTmpStates) newTmpStates
  where
    generatedRules :: [DFARule a b]
    generatedRules = concat $ L.map (\x -> genDFARule' x rs) tmpStates
    newTmpStates = L.filter (\x -> not (elem x visitedStates)) $ L.map (\(D.Rule _ _ x) -> x) generatedRules
genDFARule'' rs acc visitedStates tmpStates
  | L.null newTmpStates = acc ++ generatedRules
  | otherwise = genDFARule'' rs (generatedRules ++ acc) (visitedStates ++ newTmpStates) newTmpStates
  where
    generatedRules :: [DFARule a b]
    generatedRules = concat $ L.map (\x -> genDFARule' x rs) tmpStates
    newTmpStates = L.filter (\x -> not (elem x visitedStates)) $ L.map (\(D.Rule _ _ x) -> x) generatedRules