loopy-0.0: Avalon.hs
{-# LANGUAGE ScopedTypeVariables #-}
module Avalon where
import System.Environment
import System.Random
import Control.Monad
import System.Directory
import System.Cmd
import Data.Char
import Data.Maybe
import Data.List
import Numeric
import System.FilePath
import Numeric.LinearAlgebra.LAPACK
import Data.Packed.Matrix hiding (Matrix)
import Data.Packed.Vector
import Data.Complex
import Types
import FeedingRates
import Stab
--not finished yet
changeChemoProp :: Foodweb -> Double -> Double -> Foodweb --first is frondose, second is rangeomorph prop osmo
changeChemoProp (Foodweb names info wij cm) cf cr = Foodweb names (changeInfo info) (changeWij wij) cm
where
changeInfo (fl:fm:fs:rl:rm:rs:rest) = frond fl: frond fm : frond fs : rangeo rl: rangeo rm: rangeo rs: rest
where
frond x = x{aeff =(cf*0.3+(1-cf)*0.8) , peff =(cf*0.8+(1-cf)*0.3) }
rangeo x = x{aeff =(cr*0.3+(1-cr)*0.8) , peff =(cr*0.8+(1-cr)*0.3) }
changeWij wij = mapMatrixInd f wij
where
f i j x|i==11 && j >= 1 && j <=3 =cf*100 -- |i==12 && j >= 1 && j <=3 =cr*100
|i==11 && j >= 4 && 6 <=3 =cf*100 -- |i==12 && j >= 1 && j <=3 =cr*100
|otherwise = x
createChemoRange :: FilePath -> Int-> IO ()
createChemoRange fp n = do
fw <- readFoodweb fp
createDirectoryIfMissing True (dropExtension fp ++ "ChemoRange")
sequence_ [writeFoodweb file $ changeChemoProp fw x y
| x <- [0,1/(fromIntegral n)..1], y <- [0,1/(fromIntegral n)..1], let file = dropExtension fp ++ "ChemoRange"</> dropExtension fp ++ "_" ++ show3dp x ++ "_" ++ show3dp y ++ ".fw"]
createOsmoRange :: FilePath -> Int-> IO ()
createOsmoRange fp n = do
fw <- readFoodweb fp
createDirectoryIfMissing True (dropExtension fp ++ "OsmoRange")
sequence_ [writeFoodweb file $ changeFeedingStrategy fw x y
| x <- [0,1/(fromIntegral n)..1], y <- [0,1/(fromIntegral n)..1], let file = dropExtension fp ++ "OsmoRange"</> dropExtension fp ++ "_" ++ show3dp x ++ "_" ++ show3dp y ++ ".fw"]
createOsmoRange2 :: FilePath -> Int-> IO ()
createOsmoRange2 fp n = do
fw <- readFoodweb fp
createDirectoryIfMissing True (dropExtension fp ++ "OsmoRange2")
sequence_ [writeFoodweb file $ changeFS2 fw x y
| x <- [0,1/(fromIntegral n)..1], y <- [0,1/(fromIntegral n)..1], let file = dropExtension fp ++ "OsmoRange2"</> dropExtension fp ++ "_" ++ show3dp x ++ "_" ++ show3dp y ++ ".fw"]
{-
createFeedingRange :: FilePath -> [Int]-> IO ()
createFeedingRange fp = do
fw <- return$ fileToFoodweb fp
--createDirectoryIfMissing True (dropExtension fp ++ "SpeciesRange")
let file = [dropExtension fp ++ "SpeciesRange"</> dropExtension fp ++ ".fw"]
writeFoodweb file $ changeFeeding fw [2,2,2,3,3,3]
return()
-}
changeFeeding :: Foodweb -> [Int] -> Foodweb
changeFeeding (Foodweb names info wij cm) fts = Foodweb names (changeInfoSp info fts) (changeWijSp wij fts ((length names))) cm -- note that cm will be wrong
generateFeedingTypes :: Int -> [[Int]]
generateFeedingTypes n = undefined --[k|k<-(replicate n i) && i<-[1..3] ]
changePlanktonicBiomass :: Foodweb -> [Double] -> Foodweb
changePlanktonicBiomass (Foodweb names info wij cm) bm = Foodweb names (changeBiomass info) wij cm
where
changeBiomass (a:b:c:d:e:f:p:hb:ppp:rest) = a:b:c:d:e:f:pro p:het hb:prim ppp:rest
where
pro x = x{biomass =bm!!1}
het x =x{biomass =bm!!2}
prim x =x{biomass =bm!!3}
----update to include chemo stuff
changeInfoSp :: [Info] -> [Int] -> [Info]
changeInfoSp is [] = basicInfo is
changeInfoSp (i:is) (ft:fts) = [change1 i ft] ++ changeInfoSp is fts
where
change1 x t = if t==1 then x{aeff =0.3 , peff =0.8 } else
if t==2 then x{aeff = 0.8 , peff = 0.11 } else
x{aeff =1 , peff =0.3 }
----update to include chemo stuff
changeWijSp :: Matrix Double -> [Int] -> Int -> Matrix Double
changeWijSp ws [] det = ws
changeWijSp wij fts det= mapMatrixInd f wij -- det is detrius row, found using getDetRow
where
n = 5 + length fts
stPl = length fts
enPl = length fts + 3
chemo = [i| (i,j)<- zip [1..] fts, j ==1]
sf = [i| (i,j)<- zip [1..] fts, j ==2]
osmo = [i| (i,j)<- zip [1..] fts, j ==3]
f i j x|i >stPl && i <=enPl && j `elem` sf =33.33
|i ==det && j `elem` osmo =100
|otherwise = x
--returns just a list of the last 5 info
basicInfo :: [Info] -> [Info]
basicInfo (i:is) = if (length (i:is))> 5 then basicInfo is else (i:is)
{-----
-}
outputAlpha :: FilePath -> IO ()
outputAlpha fp = do
fw1<- readFoodweb fp
let fw = checkFoodweb fw1
let alpha = getCommat fw
writeFile (dropExtension fp ++".alpha") (outputMatrix $ matrixDoubleToString alpha)
return()
-- print $ alphaijElem info wij res 14 0
checkFoodweb :: Foodweb -> Foodweb
checkFoodweb fw = deleteSps fw b0
where b0 = [i | (i,j) <- zip [0..] (info fw), biomass j == 0]--if biomass ==0 output col number
checkFoodweb2 :: Foodweb->Foodweb
checkFoodweb2 fw = fw{cm=getCommat fw}
getDetRow :: Foodweb -> [Int]
getDetRow fw = [i | (i,j) <- zip [0..] (info fw), deathRate j==0]
{-----}
changeInfo :: Foodweb -> Maybe Double ->Maybe Double -> Maybe [Double] -> Maybe [Double] -> Maybe Double-> Foodweb
changeInfo (Foodweb names info wij cm) marealCoverage mrFRatio msizeClassesF msizeClassesR mareaBiomassRatio = Foodweb names (change info) wij cm
where change = if mrFRatio==Just 0 then changeF else
if mrFRatio==Just 1 then changeR else
changeInfo
where
changeInfo (fl:fm:fs:rl:rm:rs:rest) = frond fl 0: frond fm 1: frond fs 2: rangeo rl 0: rangeo rm 1: rangeo rs 2: rest--numbers refer to sizeclasses
changeF (fl:fm:fs:rest) = frond fl 0: frond fm 1: frond fs 2: rest--numbers refer to sizeclasses
changeR (rl:rm:rs:rest) = rangeo rl 0: rangeo rm 1: rangeo rs 2: rest--numbers refer to sizeclasses
frond x y= x{biomass = (arealCoverage*(1-rFRatio)*(sizeClassesF!!y)*areaBiomassRatio)}
rangeo x y= x{biomass = (arealCoverage*rFRatio*(sizeClassesR!!y)*areaBiomassRatio)}
arealCoverage = fromMaybe 0.1 marealCoverage
rFRatio = fromMaybe 0.5 mrFRatio
sizeClassesR = fromMaybe [0.95,0.045,0.005] msizeClassesR -- need to extend to rangeo and fronds
sizeClassesF = fromMaybe [0.9,0.09,0.01] msizeClassesF -- need to extend to rangeo and fronds
areaBiomassRatio = fromMaybe 1000 mareaBiomassRatio
changeFS2 :: Foodweb -> Double -> Double -> Foodweb --first is frondose, second is rangeomorph prop osmo
changeFS2 (Foodweb names info wij cm) cf cr = Foodweb names (changeInfo info) (changeWij wij) cm
where
changeInfo (sp1:sp2:rest) = species1 sp1: species2 sp2 : rest
where
species1 x = x{aeff =(cf*1+(1-cf)*0.8) , peff =(cf*0.3+(1-cf)*0.11) }
species2 x = x{aeff =(cr*1+(1-cr)*0.8) , peff =(cr*0.3+(1-cr)*0.11) }
changeWij wij = mapMatrixInd f wij
where
f i j x|i >=5 && i <=7 && j == 1 =(1-cf)*100
|i >=5 && i <=7 && j == 2 =(1-cr)*100
|i==9 && j ==1 =cf*100 -- |i==12 && j >= 1 && j <=3 =cr*100
|i==9 && j ==2 =cr*100 -- |i==12 && j >= 1 && j <=3 =cr*100
|otherwise = x
--needs create a food web before going in
changeFeedingStrategy :: Foodweb -> Double -> Double -> Foodweb --first is frondose, second is rangeomorph prop osmo
changeFeedingStrategy (Foodweb names info wij cm) cf cr = Foodweb names (changeInfo info) (changeWij wij) cm
where
changeInfo (fl:fm:fs:rl:rm:rs:rest) = frond fl: frond fm : frond fs : rangeo rl: rangeo rm: rangeo rs: rest
where
frond x = x{aeff =(cf*1+(1-cf)*0.8) , peff =(cf*0.3+(1-cf)*0.11) }
rangeo x = x{aeff =(cr*1+(1-cr)*0.8) , peff =(cr*0.3+(1-cr)*0.11) }
changeWij wij = mapMatrixInd f wij
where
f i j x|i >=7 && i <=9 && j >= 1 && j <=3 =(1-cf)*100
|i >=7 && i <=9 && j >= 4 && j <=6 =(1-cr)*100
|i==11 && j >= 1 && j <=3 =cf*100 -- |i==12 && j >= 1 && j <=3 =cr*100
|i==11 && j >= 4 && j <=6 =cr*100 -- |i==12 && j >= 1 && j <=3 =cr*100
|otherwise = x
----
--- changing the biomass in some way
-- three things influence the biomasses:
--(1) total biota coverage of bedding plane - default 0.10
--(2) prop of rangeo:frond - default 0.5
--(3) prop of size classes in each tier - default [0.9,0.09,0.01]
--(4) the area to biomass ratio - default 1000
--each size class is given by 1*2*3
changeBiomass :: Foodweb -> Maybe Double ->Maybe Double -> Maybe [Double] -> Maybe [Double] -> Maybe Double-> Foodweb
changeBiomass (Foodweb names info wij cm) marealCoverage mrFRatio msizeClassesF msizeClassesR mareaBiomassRatio = Foodweb names (changeInfo info) wij cm
where
changeInfo (fl:fm:fs:rl:rm:rs:rest) = frond fl 0: frond fm 1: frond fs 2: rangeo rl 0: rangeo rm 1: rangeo rs 2: rest--numbers refer to sizeclasses
frond x y= x{biomass = (arealCoverage*(1-rFRatio)*(sizeClassesF!!y)*areaBiomassRatio)}
rangeo x y= x{biomass = (arealCoverage*rFRatio*(sizeClassesR!!y)*areaBiomassRatio)}
arealCoverage = fromMaybe 0.1 marealCoverage
rFRatio = fromMaybe 0.5 mrFRatio
sizeClassesR = fromMaybe [0.95,0.045,0.005] msizeClassesR -- need to extend to rangeo and fronds
sizeClassesF = fromMaybe [0.9,0.09,0.01] msizeClassesF -- need to extend to rangeo and fronds
areaBiomassRatio = fromMaybe 1000 mareaBiomassRatio
changeBiomass2 :: Foodweb -> Maybe Double ->Maybe Double -> Maybe [Double] -> Maybe [Double] -> Maybe Double-> Foodweb
changeBiomass2 (Foodweb names info wij cm) marealCoverage mrFRatio msizeClassesF msizeClassesR mareaBiomassRatio = changeInfo (changeFoodweb (Foodweb names info wij cm) mrFRatio) marealCoverage mrFRatio msizeClassesF msizeClassesR mareaBiomassRatio
changeFoodweb :: Foodweb -> Maybe Double-> Foodweb
changeFoodweb fw r = if r == Just 0 --r is the ratio of rangeomorphs to fronds
then
deleteSp (deleteSp (deleteSp fw 3) 3) 3
else
if r == Just 1
then
deleteSp (deleteSp (deleteSp fw 0) 0) 0
else
fw
fileToFoodweb2 :: FilePath -> IO Foodweb
fileToFoodweb2 fp = do
y <- fileToFoodweb fp
return $ y{cm=getCommat y} -- FIXME: Reorder to remove this
{-
-}
--takes away any zero biomass species NEED TO FINISH THIS OFF PROPERLY
--needs to be an ordered list
deleteSps :: Foodweb -> [Int] -> Foodweb
deleteSps fw [] = fw
deleteSps fw spNu = deleteSps (deleteSp fw (head spNu)) (reduceListNu (tail spNuO))
where spNuO = spNu
reduceListNu :: [Int] -> [Int]
reduceListNu [] = []
reduceListNu (x:xs) = [x-1] ++ reduceListNu xs
deleteSp :: Foodweb -> Int -> Foodweb
deleteSp (Foodweb names info wij cm) spNu = Foodweb (delListLine spNu names) (delListLine spNu info) (delListListLine spNu wij) cm
delListLine :: Int->[a]->[a]
delListLine i xs =take i xs ++ drop (i+1) xs -- deleting line i from xs, with numbers starting at 0
delListListLine :: Int -> [[a]] -> [[a]]
delListListLine i xs = map (delListLine i) (delListLine i xs)
createFrondRange :: FilePath -> Int -> Int -> IO () -- assumes fronds and rangeomorphs behave in the same way
createFrondRange fp n1 n2 = do
fw <- readFoodweb fp
createDirectoryIfMissing True (dropExtension fp ++ "FrondRange")
sequence_ [writeFoodweb file $ changeFeedingStrategy (changeBiomass2 fw Nothing (Just y) Nothing Nothing Nothing) x x
| x <- [0,1/(fromIntegral n1)..1], y <- [0,1/(fromIntegral n2)..1], let file = dropExtension fp ++ "FrondRange"</> dropExtension fp ++ "_" ++ show3dp y ++ "_" ++ show3dp x ++ ".fw"]