From 173d34c0d529830efeab39b7cca9a03856514469 Mon Sep 17 00:00:00 2001 From: Michael Orlitzky Date: Thu, 1 Sep 2011 20:23:57 -0400 Subject: [PATCH] Use an IArray for the cubes and cube_at functions. --- src/Grid.hs | 58 +++++++++++++++++++++++++++-------------------------- 1 file changed, 30 insertions(+), 28 deletions(-) diff --git a/src/Grid.hs b/src/Grid.hs index ab698c1..8bf8382 100644 --- a/src/Grid.hs +++ b/src/Grid.hs @@ -4,6 +4,7 @@ module Grid where +import Data.Array (Array, array, (!)) import qualified Data.Array.Repa as R import Test.QuickCheck (Arbitrary(..), Gen, Positive(..)) @@ -15,6 +16,9 @@ import Tetrahedron (polynomial) import Values (Values3D, dims, empty3d, zoom_shape) +type CubeGrid = Array (Int,Int,Int) Cube + + -- | Our problem is defined on a Grid. The grid size is given by the -- positive number h. The function values are the values of the -- function at the grid points, which are distance h from one @@ -44,18 +48,24 @@ empty_grid :: Grid empty_grid = Grid 1 empty3d --- | Returns a three-dimensional list of cubes centered on the grid +-- | Returns a three-dimensional array of cubes centered on the grid -- points of g with the appropriate 'FunctionValues'. -cubes :: Grid -> [[[Cube]]] +cubes :: Grid -> CubeGrid cubes g - | xsize == 0 || ysize == 0 || zsize == 0 = [[[]]] - | otherwise = - [[[ Cube (h g) i j k (make_values fvs i j k) | i <- [0..xsize]] - | j <- [0..ysize]] - | k <- [0..zsize]] - where - fvs = function_values g - (xsize, ysize, zsize) = dims fvs + = array (lbounds, ubounds) + [ ((i,j,k), cube_ijk) + | i <- [0..xmax], + j <- [0..ymax], + k <- [0..zmax], + let cube_ijk = Cube (h g) i j k (make_values fvs i j k)] + where + xmax = xsize - 1 + ymax = ysize - 1 + zmax = zsize - 1 + lbounds = (0, 0, 0) + ubounds = (xmax, ymax, zmax) + fvs = function_values g + (xsize, ysize, zsize) = dims fvs -- | Takes a grid and a position as an argument and returns the cube @@ -63,24 +73,16 @@ cubes g -- position is outside of the grid), it will throw an error. cube_at :: Grid -> Int -> Int -> Int -> Cube cube_at g i j k - | i < 0 = error "i < 0 in cube_at" - | j < 0 = error "j < 0 in cube_at" - | k < 0 = error "k < 0 in cube_at" - | otherwise = - let zsize = length (cubes g) in - if k >= zsize then - error "k >= xsize in cube_at" - else - let ysize = length ((cubes g) !! k) in - if j >= ysize then - error "j >= ysize in cube_at" - else - let xsize = length (((cubes g) !! k) !! j) in - if i >= xsize then - error "i >= xsize in cube_at" - else - (((cubes g) !! k) !! j) !! i - + | i < 0 = error "i < 0 in cube_at" + | i >= xsize = error "i >= xsize in cube_at" + | j < 0 = error "j < 0 in cube_at" + | j >= ysize = error "j >= ysize in cube_at" + | k < 0 = error "k < 0 in cube_at" + | k >= zsize = error "k >= zsize in cube_at" + | otherwise = (cubes g) ! (i,j,k) + where + fvs = function_values g + (xsize, ysize, zsize) = dims fvs -- The first cube along any axis covers (-h/2, h/2). The second -- covers (h/2, 3h/2). The third, (3h/2, 5h/2), and so on. -- 2.43.2