dobutokO-poetry (empty) → 0.1.0.0
raw patch · 6 files changed
+241/−0 lines, 6 filesdep +basedep +mmsyn6ukrdep +mmsyn7ssetup-changed
Dependencies added: base, mmsyn6ukr, mmsyn7s, vector
Files
- ChangeLog.md +5/−0
- DobutokO/Poetry.hs +150/−0
- LICENSE +20/−0
- Main.hs +30/−0
- Setup.hs +2/−0
- dobutokO-poetry.cabal +34/−0
+ ChangeLog.md view
@@ -0,0 +1,5 @@+# Revision history for dobutokO-poetry++## 0.1.0.0 -- 2020-06-01++* First version. Released on an unsuspecting world.
+ DobutokO/Poetry.hs view
@@ -0,0 +1,150 @@+-- |+-- Module : DobutokO.Poetry+-- Copyright : (c) OleksandrZhabenko 2020+-- License : MIT+-- Stability : Experimental+-- Maintainer : olexandr543@yahoo.com+--+-- Helps to order the 7 or less Ukrainian words (or their concatenations) +-- to obtain somewhat suitable for poetry or music text.++{-# LANGUAGE BangPatterns #-}++module DobutokO.Poetry (+ -- * Main functions+ uniq10Poetical4+ , uniq10Poetical5+ , uniq10PoeticalG+ -- * Additional functions+ , uniquenessVariantsG+ , uniquenessVariants3+ , uniquenessVariants4+ , uniqMaxPoeticalG+ , uniqInMaxPoetical+ -- * Different norms+ , norm1+ , norm2+ , norm3+ , norm4+ , norm5+ -- * Help functions+ , fourFrom5+ , lastFrom5 +) where++import Data.Char (isPunctuation)+import qualified Data.Vector as V+import Data.List ((\\))+import MMSyn7s ++-- | A variant of 'uniquesessVariantsG' with the norm being 'norm3'.+uniquenessVariants3 :: String -> V.Vector ([Int],Int,Int,Int,String)+uniquenessVariants3 = uniquenessVariantsG norm3++-- | A variant of 'uniquesessVariantsG' with the norm being 'norm4'.+uniquenessVariants4 :: String -> V.Vector ([Int],Int,Int,Int,String)+uniquenessVariants4 = uniquenessVariantsG norm4++-- | Given a 'String' consisting of no more than 7 Ukrainian words [some of them can be created by concatenation with preserving the Ukrainian +-- pronunciation of the parts, e. g. \"так як\" (actually two correnc Ukrainian words) can be written \"такйак\" (one phonetical Ukrainian word +-- obtained with preserving phonetical structure), if you would not like to treat them separately] it returns a 'V.Vector' of possible combinations +-- without repeating of the words in differnet order and for every one of them appends also information about 'uniquenessPeriods' to it and finds out +-- three different metrics -- named \"norms\". Afterwards, depending on these norms it can be specified some phonetical properties of the words that +-- allow to use them poetically or to create a varied melody with them. Some variants of this generalized function are 'uniquesessVariants3' and +-- 'uniquesessVariants4' with the predefined norms.+uniquenessVariantsG :: ([Int] -> Int) -> String -> V.Vector ([Int],Int,Int,Int,String)+uniquenessVariantsG g xs + | null xs = V.empty+ | otherwise = + case V.length . V.fromList . take 7 . words $ xs of + 7 -> + V.fromList . map ((\vs -> let !rs = uniquenessPeriods vs in (rs, norm1 rs, norm2 rs, g rs, vs)) . unwords . V.toList . + V.backpermute (V.fromList . take 7 . words $ xs)) $ + ([V.fromList [x1,x2,x3,x4,x5,x6,x7] | !x1 <- [0..6], !x2 <- [0..6] \\ [x1], !x3 <- [0..6] \\ [x1,x2], !x4 <- [0..6] \\ [x1,x2,x3], + !x5 <- [0..6] \\ [x1,x2,x3,x4], !x6 <- [0..6] \\ [x1,x2,x3,x4,x5], !x7 <- [0..6] \\ [x1,x2,x3,x4,x5,x6]]::[V.Vector Int])+ 6 -> + V.fromList . map ((\vs -> let rs = uniquenessPeriods vs in (rs, norm1 rs, norm2 rs, g rs, vs)) . unwords . V.toList . + V.backpermute (V.fromList . take 7 . words $ xs)) $+ ([V.fromList [x1,x2,x3,x4,x5,x6] | !x1 <- [0..5], !x2 <- [0..5] \\ [x1], !x3 <- [0..5] \\ [x1,x2], !x4 <- [0..5] \\ [x1,x2,x3], + !x5 <- [0..5] \\ [x1,x2,x3,x4], !x6 <- [0..5] \\ [x1,x2,x3,x4,x5]]::[V.Vector Int])+ 5 -> + V.fromList . map ((\vs -> let rs = uniquenessPeriods vs in (rs, norm1 rs, norm2 rs, g rs, vs)) . unwords . V.toList . + V.backpermute (V.fromList . take 7 . words $ xs)) $+ ([V.fromList [x1,x2,x3,x4,x5] | !x1 <- [0..4], !x2 <- [0..4] \\ [x1], !x3 <- [0..4] \\ [x1,x2], !x4 <- [0..4] \\ [x1,x2,x3], + !x5 <- [0..4] \\ [x1,x2,x3,x4]]::[V.Vector Int])+ 4 -> + V.fromList . map ((\vs -> let rs = uniquenessPeriods vs in (rs, norm1 rs, norm2 rs, g rs, vs)) . unwords . V.toList . + V.backpermute (V.fromList . take 7 . words $ xs)) $+ ([V.fromList [x1,x2,x3,x4] | !x1 <- [0..3], !x2 <- [0..3] \\ [x1], !x3 <- [0..3] \\ [x1,x2], !x4 <- [0..3] \\ [x1,x2,x3]]::[V.Vector Int])+ 3 -> + V.fromList . map ((\vs -> let rs = uniquenessPeriods vs in (rs, norm1 rs, norm2 rs, g rs, vs)) . unwords . V.toList . + V.backpermute (V.fromList . take 7 . words $ xs)) $ ([V.fromList [x1,x2,x3] | !x1 <- [0..2], !x2 <- [0..2] \\ [x1], + !x3 <- [0..2] \\ [x1,x2]]::[V.Vector Int])+ 2 -> + V.fromList . map ((\vs -> let rs = uniquenessPeriods vs in (rs, norm1 rs, norm2 rs, g rs, vs)) . unwords . V.toList . + V.backpermute (V.fromList . take 7 . words $ xs)) $ ([V.fromList [x1,x2] | !x1 <- [0,1], !x2 <- [0,1] \\ [x1]]::[V.Vector Int])+ _ -> V.empty+ +-- | A first norm for the list of positive 'Int'. For not empty lists equals to the maximum element.+norm1 :: [Int] -> Int +norm1 xs + | null xs = 0+ | otherwise = maximum xs++-- | A second norm for the list of positive 'Int'. For not empty lists equals to the sum of the elements.+norm2 :: [Int] -> Int+norm2 xs = sum xs ++-- | A third norm for the list of positive 'Int'. For not empty lists equals to the sum of the doubled maximum element and a rest elements of the list.+norm3 :: [Int] -> Int+norm3 xs + | null xs = 0+ | otherwise = maximum xs + sum xs++-- | A fourth norm for the list of positive 'Int'. Equals to the sum of the 'norm3' and 'norm2'.+norm4 :: [Int] -> Int+norm4 xs + | null xs = 0+ | otherwise = maximum xs + sum xs + maximum (xs \\ [maximum xs])++-- | A fifth norm for the list of positive 'Int'. For not empty lists equals to the sum of the elements quoted with sum of the two most minimum elements.+norm5 :: [Int] -> Int+norm5 xs + | null xs = 0+ | otherwise = sum xs `quot` (minimum xs + minimum (xs \\ [minimum xs]))++-- | Given a norm and a Ukrainian 'String' consisting of no more than 7 words (see also the information for 'uniquenessVariantG') returns the maximum by the+-- specified norm element of the 'uniquenessVariantsG' applied to the same arguments.+uniqMaxPoeticalG :: ([Int] -> Int) -> String -> ([Int],Int,Int,Int,String)+uniqMaxPoeticalG g = V.maximumBy (\(_,_,_,x30,_) (_,_,_,x31,_) -> compare x30 x31) . uniquenessVariantsG g++fourFrom5 :: (a,b,b,b,c) -> (a,b,b,b)+fourFrom5 (x,y0,y1,y2,_) = (x,y0,y1,y2)++lastFrom5 :: (a,b,b,b,c) -> c+lastFrom5 (_,_,_,_,z) = z++-- | Similar to 'uniqMaxPoeticalG' but instead of resulting in a maximum element, outputs it by parts and returns the rest of the 'V.Vector' without this +-- maximum element.+uniqInMaxPoetical :: V.Vector ([Int],Int,Int,Int,String) -> IO (V.Vector ([Int],Int,Int,Int,String))+uniqInMaxPoetical v = do+ let !uniq = V.maximumBy (\(_,_,_,x30,_) (_,_,_,x31,_) -> compare x30 x31) v+ putStrLn (filter (not . isPunctuation) . lastFrom5 $ uniq) >> print (fourFrom5 uniq) >> putStrLn "" + return . V.filter (/= uniq) $ v++-- | Recursive 10 times application of the 'uniqInMaxPoetical' function. Prints 10 (or less if there are less of them) maximum elements starting from +-- the first and further to the rest. The norm given defines the way, in which the elements are considered the \"maximum\" ones.+uniq10PoeticalG :: ([Int] -> Int) -> String -> IO ()+uniq10PoeticalG g xs = let v = uniquenessVariantsG g xs in uniqInMaxPoetical v >>= uniqInMaxPoetical >>= uniqInMaxPoetical >>= uniqInMaxPoetical >>= uniqInMaxPoetical + >>= uniqInMaxPoetical >>= uniqInMaxPoetical >>= uniqInMaxPoetical >>= uniqInMaxPoetical >>= uniqInMaxPoetical >> return ()++-- | A variant of 'uniq10PoeticalG' with the 'norm4' applied. The list is (according to some model, not universal, but a reasonable one in the most cases) the +-- most suitable for intonation changing and, therefore, for the accompaniment of the highly changable or variative melody.+uniq10Poetical4 :: String -> IO ()+uniq10Poetical4 = uniq10PoeticalG norm4++-- | A variant of 'uniq10PoeticalG' with the 'norm5' applied. The list is (according to some model, not universal, but a reasonable one in the most cases) the +-- most suitable for rhythmic speech and two-syllabilistic-based poetry. Therefore, it can be used to create a poetic composition or to emphasize some +-- thoughts.+uniq10Poetical5 :: String -> IO ()+uniq10Poetical5 = uniq10PoeticalG norm5
+ LICENSE view
@@ -0,0 +1,20 @@+Copyright (c) 2020 OleksandrZhabenko++Permission is hereby granted, free of charge, to any person obtaining+a copy of this software and associated documentation files (the+"Software"), to deal in the Software without restriction, including+without limitation the rights to use, copy, modify, merge, publish,+distribute, sublicense, and/or sell copies of the Software, and to+permit persons to whom the Software is furnished to do so, subject to+the following conditions:++The above copyright notice and this permission notice shall be included+in all copies or substantial portions of the Software.++THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.+IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY+CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,+TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE+SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ Main.hs view
@@ -0,0 +1,30 @@+-- |+-- Module : Main+-- Copyright : (c) OleksandrZhabenko 2020+-- License : MIT+-- Stability : Experimental+-- Maintainer : olexandr543@yahoo.com+--+-- Helps to order the 7 or less Ukrainian words (or their concatenations) +-- to obtain somewhat suitable for poetry or music text.++module Main where++import DobutokO.Poetry (uniq10Poetical4,uniq10Poetical5)+import System.Environment (getArgs)+import Melodics.Executable (workWithInput)++-- | The first command line argument specifies which function to run. If given \"4\" it runs 'uniq10Poetical4', otherwise 'uniq10Poetical5'. The next 7 +-- are treated as the Ukrainian words to be ordered accordingly to the norm. For more information, please, refer to the documentation for the abovementioned +-- functions. +-- +-- Afterwards, you can generate a sounding using 'workWithInput' in the \".wav\" format.+main :: IO ()+main = do + args <- getArgs+ let arg0 = concat . take 1 $ args+ word1s = unwords . drop 1 $ args+ if arg0 == "4" then uniq10Poetical4 word1s else uniq10Poetical5 word1s+ putStrLn "What string would you like to record as a Ukrainian text sounding by mmsyn6ukr package? "+ str <- getLine+ workWithInput str 1
+ Setup.hs view
@@ -0,0 +1,2 @@+import Distribution.Simple+main = defaultMain
+ dobutokO-poetry.cabal view
@@ -0,0 +1,34 @@+-- Initial dobutokO-poetry.cabal generated by cabal init. For further+-- documentation, see http://haskell.org/cabal/users-guide/++name: dobutokO-poetry+version: 0.1.0.0+synopsis: Helps to order the 7 or less Ukrainian words to obtain somewhat suitable for poetry or music text+description: Helps to order the 7 or less Ukrainian words (or their concatenations) to obtain somewhat suitable for poetry or music text.++homepage: https://hackage.haskell.org/package/dobutokO-poetry+license: MIT+license-file: LICENSE+author: OleksandrZhabenko+maintainer: olexandr543@yahoo.com+-- copyright:+category: Language, Game+build-type: Simple+extra-source-files: ChangeLog.md+cabal-version: >=1.10++library+ exposed-modules: DobutokO.Poetry, Main+ -- other-modules:+ other-extensions: BangPatterns+ build-depends: base >=4.7 && <4.15, vector >=0.11 && <0.14, mmsyn7s >=0.6.7 && <1, mmsyn6ukr >=0.7.2 && <1+ -- hs-source-dirs:+ default-language: Haskell2010++executable dobutokO-poetry+ main-is: Main.hs+ other-modules: DobutokO.Poetry+ other-extensions: BangPatterns+ build-depends: base >=4.7 && <4.15, vector >=0.11 && <0.14, mmsyn7s >=0.6.7 && <1, mmsyn6ukr >=0.7.2 && <1+ -- hs-source-dirs:+ default-language: Haskell2010