1

Hello everyone I am beginner in Haskell, I have a dat file that contains

[("img0.bmp", [0,0])
,("img1.bmp", [0,1])
,("img2.bmp", [1,0])
,("img3.bmp", [1,1])]

the strings are images files in a folder so basically I need to read file including many files as inputs , I am trying to have at the end [([Double],[Double])] extracting matrix from bmp files and turn that into [Double]

I have tried something like this

learnbmp = do
 vs <- getArgs
 df <- run (readFile (vs!!0))
 let ds = Prelude.read df :: [(String,[Double])]
 let ns = Prelude.unzip ds 

 --let a =  Prelude.map (\(v) -> toUnboxed  (readImageFromBMPa v))(fst ns)
 let a =  fst ns
 let b = snd ns 
 --let n' =  Prelude.map (\(v) -> ((readMatrixfromImage v) ) ) a
 let n' =  Prelude.map (\(v) -> ((readMatrixfromImage v) ) ) a

 let final = Prelude.zip n' b 
 
 return final

the type of final is

final :: [(IO (Vector Word8), [Double])]

with the function readMatrixfromImage is defined like this

readMatrixfromImage :: FilePath -> IO (Vector Word8)
readMatrixfromImage image = do 
       x <- readImageFromBMPa image -- 'x' est alors de type t
       let (Right r) = x
       let a = toUnboxed r
       return a

any help would be appreciated thank you

Winssen
  • 53
  • 5
  • "*I am trying to have at the end `[([Double],[Double])]`*". It does not make much sense that `learnbmp` returns `[([Double, Double])]`, since it involves an `IO`, it should have type `IO [([Double], [Double])]`. – Willem Van Onsem Dec 27 '20 at 13:37
  • so there is no way to have [([Double],[Double])] in this case right – Winssen Dec 27 '20 at 13:39
  • 1
    while one can use `unsafePerformIO`, that would really be a (very) bad idea, since it basically means the "side effect container" IO creates is destroyed: https://stackoverflow.com/questions/16773528/haskell-how-to-convert-from-io-a-to-a – Willem Van Onsem Dec 27 '20 at 13:41
  • Taking a step back, why does your input file contain what looks like a snippet of Haskell code, rather than JSON or some other language-agnostic format? – chepner Dec 28 '20 at 19:32

1 Answers1

2

If you want to obtain the results "wrapped" in the IO monad, you can use mapM :: (Monad m, Traversable t) => (a -> m b) -> t a -> m (t b):

learnbmp :: IO [([Double],[Double])]
learnbmp = do
    (v0:_) <- getArgs
    df <- run (readFile v0)
    let (a, b) = Prelude.unzip (Prelude.read df :: [(String,[Double])])
    (`Prelude.zip` b) <$> mapM readMatrixfromImage a

Here the learnbmp thus has type IO [([Double], [Double])]. It is thus an IO action that will result in an item of type [([Double], [Double])], and you can thus use learnbmp in other expressions that result in a type IO a like main.

Willem Van Onsem
  • 443,496
  • 30
  • 428
  • 555