sloane 2.0.3 → 2.0.4
raw patch · 6 files changed
+41/−36 lines, 6 filesdep +stringsearch
Dependencies added: stringsearch
Files
- README.md +1/−1
- Sloane/Config.hs +1/−1
- Sloane/DB.hs +21/−16
- sloane.1 +1/−1
- sloane.cabal +3/−2
- sloane.hs +14/−15
README.md view
@@ -1,5 +1,5 @@ ----title: SLOANE(1) Sloane User Manual | Version 2.0.3+title: SLOANE(1) Sloane User Manual | Version 2.0.4 date: 7 Jan 2015 ---
Sloane/Config.hs view
@@ -29,7 +29,7 @@ h <- getHomeDirectory let dsloane = h </> ".sloane" return Config- { nameVer = "sloane 2.0.3"+ { nameVer = "sloane 2.0.4" , home = h , sloaneDir = dsloane , sloaneDB = dsloane </> "sloane.db"
Sloane/DB.hs view
@@ -26,6 +26,8 @@ import Prelude hiding (lookup, null, take, read) import qualified Prelude as P import Data.List (intersect)+import qualified Data.ByteString.Search as Search+import qualified Data.ByteString.Char8 as Ch8 import Data.ByteString (ByteString) import qualified Data.ByteString as B import qualified Data.ByteString.Lazy as BL@@ -43,8 +45,8 @@ import Sloane.Config import System.Directory -type ANumber = Text-type Seq = Text+type ANumber = ByteString+type Seq = ByteString type Key = Char type Entry = Text type Reply = Map Key Entry@@ -53,10 +55,10 @@ type DBRaw = Map ByteString (Map Char ByteString) encodeUtf8' :: DB -> DBRaw-encodeUtf8'= M.mapKeys encodeUtf8 . M.map (M.map encodeUtf8)+encodeUtf8'= M.map (M.map encodeUtf8) decodeUtf8' :: DBRaw -> DB-decodeUtf8' = M.mapKeys decodeUtf8 . M.map (M.map decodeUtf8)+decodeUtf8' = M.map (M.map decodeUtf8) gzCompress :: ByteString -> ByteString gzCompress = BL.toStrict . GZ.compress . BL.fromStrict@@ -82,10 +84,10 @@ putStrLn "Done." where unionDB = M.unionWith M.union- mkDB key = mkMap key . decodeUtf8 . gzDecompress- mkMap key = M.fromList . map (aNumberAndReply key) . drop 4 . T.lines- mkReply key = M.singleton key . T.dropWhile (==',') . T.drop 8- aNumberAndReply key line = (T.take 7 line, mkReply key line)+ mkDB key = mkMap key . gzDecompress+ mkMap key = M.fromList . map (aNumberAndReply key) . drop 4 . Ch8.lines+ mkReply key = M.singleton key . decodeUtf8 . Ch8.dropWhile (==',') . Ch8.drop 8+ aNumberAndReply key line = (Ch8.take 7 line, mkReply key line) read :: Config -> IO DB read cfg = doesFileExist (sloaneDB cfg) >>= \updated ->@@ -106,14 +108,17 @@ lookup :: ANumber -> DB -> Maybe Reply lookup = M.lookup -lookupSeq :: ANumber -> DB -> Maybe Seq+lookupSeq :: ANumber -> DB -> Maybe Text lookupSeq anum db = lookup anum db >>= M.lookup 'S' -grep :: Text -> DB -> DB+isInfix :: ByteString -> ByteString -> Bool+isInfix q = not . P.null . Search.indices q++grep :: ByteString -> DB -> DB grep q = M.filter $ \reply -> case M.lookup 'S' reply of Nothing -> False- Just r -> q `T.isInfixOf` r+ Just r -> q `isInfix` (encodeUtf8 r) take :: Int -> DB -> DB take n = M.fromList . P.take n . M.toList@@ -128,12 +133,12 @@ singleton :: ANumber -> Key -> Entry -> DB singleton aNum key entry = M.singleton aNum $ M.singleton key entry -parseOEISEntries :: Text -> DB+parseOEISEntries :: ByteString -> DB parseOEISEntries = unions . map parseLine . trim where- trim = map (T.drop 1) . reverse . drop 2 . reverse . drop 5 . T.lines- parseLine = parseWords . T.words- parseWords (key:aNum:rest) = singleton aNum (T.head key) (T.unwords rest)+ trim = map (Ch8.drop 1) . reverse . drop 2 . reverse . drop 5 . Ch8.lines+ parseLine = parseWords . Ch8.words+ parseWords (key:aNum:rest) = singleton aNum (Ch8.head key) (decodeUtf8 (Ch8.unwords rest)) parseWords _ = M.empty put :: Config -> [Key] -> DB -> IO ()@@ -146,7 +151,7 @@ setSGR [ SetColor Foreground Dull Green ] putStr [key] setSGR [ SetColor Foreground Dull Yellow ]- putStr " " >> IO.putStr aNum+ putStr " " >> Ch8.putStr aNum setSGR [] putStr " " >> IO.putStrLn (crop key (termWidth cfg - 10) line) putStrLn ""
sloane.1 view
@@ -1,4 +1,4 @@-.TH "SLOANE" "1" "7 Jan 2015" "Sloane User Manual" "Version 2.0.2"+.TH "SLOANE" "1" "7 Jan 2015" "Sloane User Manual" "Version 2.0.4" .SH NAME .PP sloane \- a command line interface to Sloane\[aq]s On\-Line Encyclopedia
sloane.cabal view
@@ -1,5 +1,5 @@ Name: sloane-Version: 2.0.3+Version: 2.0.4 Synopsis: A command line interface to Sloane's On-Line Encyclopedia of Integer Sequences Description: A command line interface to Sloane's On-Line Encyclopedia@@ -40,4 +40,5 @@ terminal-size >=0.2, filepath >=1.3, directory >=1.2,- zlib >=0.5+ zlib >=0.5,+ stringsearch
sloane.hs view
@@ -7,10 +7,9 @@ import Data.List (intercalate) import Data.Maybe (maybeToList) import Data.Monoid-import Data.Text (Text)-import qualified Data.Text as T import qualified Data.Text.IO as IO-import Data.Text.Encoding (decodeUtf8)+import Data.ByteString (ByteString)+import qualified Data.ByteString.Char8 as Ch8 import System.IO (isEOF) import Network.HTTP (urlEncodeVars) import Network.Curl.Download (openURI)@@ -42,18 +41,18 @@ oeisKeys = "ISTUVWXNDHFYAOEeptoKC" -- Valid OEIS keys oeisUrls :: Config -> DB -> [URL]-oeisUrls cfg = map ((oeisHost cfg ++) . T.unpack) . DB.aNumbers+oeisUrls cfg = map ((oeisHost cfg ++) . Ch8.unpack) . DB.aNumbers oeisLookup :: Options -> Config -> IO DB oeisLookup opts cfg =- (DB.parseOEISEntries . decodeUtf8 . either error id) <$>+ (DB.parseOEISEntries . either error id) <$> openURI (oeisURL cfg ++ "&" ++ urlEncodeVars [("n", show n), ("q", q)]) where n = limit opts q = unwords $ terms opts grepDB :: Options -> DB -> DB-grepDB opts = DB.take n . DB.grep (T.pack q)+grepDB opts = DB.take n . DB.grep (Ch8.pack q) where n = limit opts q = intercalate "," (terms opts)@@ -69,26 +68,26 @@ tr c = if c `elem` ";," then ' ' else c input = map read (words (map tr (unwords (terms opts)))) -dropComment :: Text -> Text-dropComment = T.takeWhile (/= '#')+dropComment :: ByteString -> ByteString+dropComment = Ch8.takeWhile (/= '#') showSeq :: [Integer] -> String showSeq = intercalate "," . map show -mkSeq :: Text -> Seq-mkSeq = T.intercalate (T.pack ",") . T.words . clean . dropComment+mkSeq :: ByteString -> Seq+mkSeq = Ch8.intercalate (Ch8.pack ",") . Ch8.words . clean . dropComment where- clean = T.filter (`elem` " 0123456789-") . T.map tr+ clean = Ch8.filter (`elem` " 0123456789-") . Ch8.map tr tr c = if c `elem` ";," then ' ' else c mkANumber :: Int -> ANumber-mkANumber n = let s = show n in T.pack ('A' : replicate (6-length s) '0' ++ s)+mkANumber n = let s = show n in Ch8.pack ('A' : replicate (6-length s) '0' ++ s) filterDB :: Options -> DB -> IO [Seq]-filterDB opts db = filter match . parseSeqs <$> IO.getContents+filterDB opts db = filter match . parseSeqs <$> Ch8.getContents where match q = (if invert opts then id else not) (DB.null $ DB.grep q db)- parseSeqs = filter (not . T.null) . map mkSeq . T.lines+ parseSeqs = filter (not . Ch8.null) . map mkSeq . Ch8.lines optionsParser :: Parser Options optionsParser =@@ -174,7 +173,7 @@ | update opts = DB.update | listTransforms opts = const $ mapM_ (putStrLn . name) transforms | anum > 0 = \c -> lookupSeq <$> DB.read c >>= mapM_ IO.putStrLn- | filtr opts = \c -> DB.read c >>= filterDB opts >>= mapM_ IO.putStrLn+ | filtr opts = \c -> DB.read c >>= filterDB opts >>= mapM_ Ch8.putStrLn | not (null tname) = const $ applyTransform opts tname | local opts = search (\o cfg -> grepDB o <$> DB.read cfg) opts | otherwise = search oeisLookup opts