
How about this: maxTableColumnWidths :: [[String]] -> [Int] maxTableColumnWidths = map (maximum . map length) Bob On 21 Feb 2009, at 22:35, Keith Sheppard wrote:
Hello,
I'm new to haskell and still getting used to working with lazy evaluation. I created a little function to calculate column widths for a 2D list of strings (a table) by iterating through the list and accumulating a max value for each column. My initial implementation ran out memory for tables with many rows because of lazy evaluation and here is how I dealt with it:
{- | for a table, calculate the max width in characters for each column -} maxTableColumnWidths :: [[String]] -> [Int] maxTableColumnWidths [] = [] maxTableColumnWidths table = maxTableColumnWidthsInternal table []
maxTableColumnWidthsInternal :: [[String]] -> [Int] -> [Int] maxTableColumnWidthsInternal [] prevMaxValues = prevMaxValues maxTableColumnWidthsInternal (row:tableTail) prevMaxValues | seqList prevMaxValues = undefined | otherwise = maxTableColumnWidthsInternal tableTail (maxRowFieldWidths row prevMaxValues)
-- this little function is for making the list strict... otherwise -- we run out of memory seqList [] = False seqList (head:tail) | head `seq` False = undefined | otherwise = seqList tail
maxRowFieldWidths :: [String] -> [Int] -> [Int] maxRowFieldWidths row prevMaxValues = let colLengths = map length row lengthOfRow = length row lengthOfPrevMax = length prevMaxValues maxPrefixList = zipWith max colLengths prevMaxValues in if lengthOfRow == lengthOfPrevMax then maxPrefixList else if lengthOfRow > lengthOfPrevMax then maxPrefixList ++ (drop lengthOfPrevMax colLengths) else maxPrefixList ++ (drop lengthOfRow prevMaxValues)
This works but it isn't very pretty (maybe also inefficient?). Is there a better way to deal with this kind of memory issue?
Thanks! Keith _______________________________________________ Beginners mailing list Beginners@haskell.org http://www.haskell.org/mailman/listinfo/beginners