{-# LANGUAGE OverloadedLists #-}
module Math.OEIS (
searchSeq, searchSeq',
lookupSeq, lookupSeq',
getSeqData, getSeqData',
extendSeq, extendSeq',
SeqData,
SearchStatus(..),
Keyword(..),
OEISSeq(..)
) where
import Data.Functor
import Data.List
import Data.Maybe (fromMaybe, listToMaybe)
import qualified Data.Vector as V
import System.IO.Unsafe (unsafePerformIO)
import Math.OEIS.Internal
import Math.OEIS.Types
searchSeq :: SearchStatus -> Int -> V.Vector OEISSeq
searchSeq :: SearchStatus -> Int -> Vector OEISSeq
searchSeq SearchStatus
ss = IO (Vector OEISSeq) -> Vector OEISSeq
forall a. IO a -> a
unsafePerformIO (IO (Vector OEISSeq) -> Vector OEISSeq)
-> (Int -> IO (Vector OEISSeq)) -> Int -> Vector OEISSeq
forall b c a. (b -> c) -> (a -> b) -> a -> c
. SearchStatus -> Int -> IO (Vector OEISSeq)
searchSeq' SearchStatus
ss
searchSeq' :: SearchStatus -> Int -> IO (V.Vector OEISSeq)
searchSeq' :: SearchStatus -> Int -> IO (Vector OEISSeq)
searchSeq' SearchStatus
ss Int
bound = do
Vector Value
results' <- SearchStatus -> Int -> Int -> Vector Value -> IO (Vector Value)
getResults SearchStatus
ss Int
0 Int
bound []
let seqs :: Vector OEISSeq
seqs
| Vector Value -> Bool
forall a. Vector a -> Bool
V.null Vector Value
results' = []
| Bool
otherwise = Value -> OEISSeq
parseOEIS (Value -> OEISSeq) -> Vector Value -> Vector OEISSeq
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Vector Value
results'
Vector OEISSeq -> IO (Vector OEISSeq)
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return Vector OEISSeq
seqs
lookupSeq :: SearchStatus -> Maybe OEISSeq
lookupSeq :: SearchStatus -> Maybe OEISSeq
lookupSeq = IO (Maybe OEISSeq) -> Maybe OEISSeq
forall a. IO a -> a
unsafePerformIO (IO (Maybe OEISSeq) -> Maybe OEISSeq)
-> (SearchStatus -> IO (Maybe OEISSeq))
-> SearchStatus
-> Maybe OEISSeq
forall b c a. (b -> c) -> (a -> b) -> a -> c
. SearchStatus -> IO (Maybe OEISSeq)
lookupSeq'
lookupSeq' :: SearchStatus -> IO (Maybe OEISSeq)
lookupSeq' :: SearchStatus -> IO (Maybe OEISSeq)
lookupSeq' SearchStatus
ss = do
Maybe Value
result <- SearchStatus -> Int -> IO (Maybe Value)
getResult SearchStatus
ss Int
0
Maybe OEISSeq -> IO (Maybe OEISSeq)
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return (Maybe OEISSeq -> IO (Maybe OEISSeq))
-> Maybe OEISSeq -> IO (Maybe OEISSeq)
forall a b. (a -> b) -> a -> b
$ case Maybe Value
result of
Just Value
result' -> OEISSeq -> Maybe OEISSeq
forall a. a -> Maybe a
Just (OEISSeq -> Maybe OEISSeq) -> OEISSeq -> Maybe OEISSeq
forall a b. (a -> b) -> a -> b
$ Value -> OEISSeq
parseOEIS Value
result'
Maybe Value
_ -> Maybe OEISSeq
forall a. Maybe a
Nothing
getSeqData :: SearchStatus -> Maybe SeqData
getSeqData :: SearchStatus -> Maybe [Integer]
getSeqData = IO (Maybe [Integer]) -> Maybe [Integer]
forall a. IO a -> a
unsafePerformIO (IO (Maybe [Integer]) -> Maybe [Integer])
-> (SearchStatus -> IO (Maybe [Integer]))
-> SearchStatus
-> Maybe [Integer]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. SearchStatus -> IO (Maybe [Integer])
getSeqData'
getSeqData' :: SearchStatus -> IO (Maybe SeqData)
getSeqData' :: SearchStatus -> IO (Maybe [Integer])
getSeqData' = ((OEISSeq -> [Integer]
seqData (OEISSeq -> [Integer]) -> Maybe OEISSeq -> Maybe [Integer]
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$>) (Maybe OEISSeq -> Maybe [Integer])
-> IO (Maybe OEISSeq) -> IO (Maybe [Integer])
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$>) (IO (Maybe OEISSeq) -> IO (Maybe [Integer]))
-> (SearchStatus -> IO (Maybe OEISSeq))
-> SearchStatus
-> IO (Maybe [Integer])
forall b c a. (b -> c) -> (a -> b) -> a -> c
. SearchStatus -> IO (Maybe OEISSeq)
lookupSeq'
extendSeq :: SeqData -> SeqData
extendSeq :: [Integer] -> [Integer]
extendSeq = IO [Integer] -> [Integer]
forall a. IO a -> a
unsafePerformIO (IO [Integer] -> [Integer])
-> ([Integer] -> IO [Integer]) -> [Integer] -> [Integer]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [Integer] -> IO [Integer]
extendSeq'
extendSeq' :: [Integer] -> IO [Integer]
extendSeq' :: [Integer] -> IO [Integer]
extendSeq' [] = [Integer] -> IO [Integer]
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return []
extendSeq' [Integer]
sd = do
Maybe OEISSeq
oeis <- SearchStatus -> IO (Maybe OEISSeq)
lookupSeq' ([Integer] -> SearchStatus
SubSeq [Integer]
sd)
[Integer] -> IO [Integer]
forall a. a -> IO a
forall (m :: * -> *) a. Monad m => a -> m a
return ([Integer] -> IO [Integer]) -> [Integer] -> IO [Integer]
forall a b. (a -> b) -> a -> b
$ case Maybe OEISSeq
oeis of
Just OEISSeq
s -> [Integer] -> [Integer] -> [Integer]
extend [Integer]
sd (OEISSeq -> [Integer]
seqData OEISSeq
s)
Maybe OEISSeq
_ -> [Integer]
sd
where
extend :: SeqData -> SeqData -> SeqData
extend :: [Integer] -> [Integer] -> [Integer]
extend [Integer]
sd [Integer]
ext = [Integer] -> Maybe [Integer] -> [Integer]
forall a. a -> Maybe a -> a
fromMaybe [Integer]
sd (Maybe [Integer] -> [Integer])
-> ([[Integer]] -> Maybe [Integer]) -> [[Integer]] -> [Integer]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ([Integer] -> Bool) -> [[Integer]] -> Maybe [Integer]
forall (t :: * -> *) a. Foldable t => (a -> Bool) -> t a -> Maybe a
find ([Integer]
sd [Integer] -> [Integer] -> Bool
forall a. Eq a => [a] -> [a] -> Bool
`isPrefixOf`) ([[Integer]] -> [Integer]) -> [[Integer]] -> [Integer]
forall a b. (a -> b) -> a -> b
$ [Integer] -> [[Integer]]
forall a. [a] -> [[a]]
tails [Integer]
ext