Ignore:
Timestamp:
Oct 4, 2006, 11:00:56 AM (18 years ago)
Author:
ole
Message:

Added functionality for getting arbitrary interpolated values in Quantity as well as calculating inundation height and location. This work was done at SUT during the last week of September 2006.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • anuga_core/source/anuga/abstract_2d_finite_volumes/quantity.py

    r3678 r3689  
    1515"""
    1616
     17from Numeric import array, zeros, Float, concatenate, NewAxis, argmax, allclose
     18from anuga.utilities.numerical_tools import ensure_numeric
    1719
    1820class Quantity:
     
    2123
    2224        from anuga.abstract_2d_finite_volumes.neighbour_mesh import Mesh
    23         from Numeric import array, zeros, Float
    2425
    2526        msg = 'First argument in Quantity.__init__ '
     
    619620
    620621
    621         from Numeric import Float
    622         from anuga.utilities.numerical_tools import ensure_numeric
    623         #from anuga.abstract_2d_finite_volumes.least_squares import fit_to_mesh
    624622        from anuga.fit_interpolate.fit import fit_to_mesh
    625623        from anuga.coordinate_transforms.geo_reference import Geo_reference
     
    754752
    755753
    756     def get_values(self, location='vertices', indices = None):
     754   
     755   
     756    def get_maximum_index(self, indices=None):
     757        """Return index for maximum value of quantity (on centroids)
     758
     759        Optional argument:
     760            indices is the set of element ids that the operation applies to.
     761
     762        Usage:
     763            i = get_maximum_index()
     764
     765        Notes:
     766            We do not seek the maximum at vertices as each vertex can
     767            have multiple values - one for each triangle sharing it.
     768
     769            If there are multiple cells with same maximum value, the first cell
     770            encountered in the triangle array is returned.
     771        """
     772
     773        V = self.get_values(location='centroids', indices=indices)
     774
     775        # Always return absolute indices
     776        i = argmax(V)
     777
     778        if indices is None:
     779            return i
     780        else:
     781            return indices[i]
     782
     783       
     784    def get_maximum_value(self, indices=None):
     785        """Return maximum value of quantity (on centroids)
     786
     787        Optional argument:
     788            indices is the set of element ids that the operation applies to.
     789
     790        Usage:
     791            v = get_maximum_value()
     792
     793        Note, we do not seek the maximum at vertices as each vertex can
     794        have multiple values - one for each triangle sharing it           
     795        """
     796
     797
     798        i = self.get_maximum_index(indices)
     799        V = self.get_values(location='centroids') #, indices=indices)
     800       
     801        return V[i]
     802       
     803
     804    def get_maximum_location(self, indices=None):
     805        """Return location of maximum value of quantity (on centroids)
     806
     807        Optional argument:
     808            indices is the set of element ids that the operation applies to.
     809
     810        Usage:
     811            x, y = get_maximum_location()
     812
     813
     814        Notes:
     815            We do not seek the maximum at vertices as each vertex can
     816            have multiple values - one for each triangle sharing it.
     817
     818            If there are multiple cells with same maximum value, the first cell
     819            encountered in the triangle array is returned.           
     820        """
     821
     822        i = self.get_maximum_index(indices)
     823        x, y = self.domain.get_centroid_coordinates()[i]
     824
     825        return x, y
     826
     827
     828
     829
     830    def get_interpolated_values(self, interpolation_points):
     831
     832        # Interpolation object based on internal (discontinuous triangles)
     833        x, y, vertex_values, triangles = self.get_vertex_values(xy=True, smooth=False)
     834        # FIXME: This concat should roll into get_vertex_values
     835        vertex_coordinates = concatenate( (x[:, NewAxis], y[:, NewAxis]), axis=1 )
     836
     837        can_reuse = False
     838        if hasattr(self, 'interpolation_object'):
     839            # Reuse to save time
     840            I = self.interpolation_object
     841
     842            if allclose(interpolation_points, I._point_coordinates):
     843                can_reuse = True
     844               
     845
     846        if can_reuse is True:       
     847            result = I.interpolate(vertex_values) # Use absence to indicate reuse
     848        else:   
     849            from anuga.fit_interpolate.interpolate import Interpolate
     850
     851            # Create interpolation object with matrix
     852            I = Interpolate(vertex_coordinates, triangles)
     853            self.interpolation_object = I
     854
     855            # Call interpolate with points the first time
     856            interpolation_points = ensure_numeric(interpolation_points, Float)                       
     857            result = I.interpolate(vertex_values, interpolation_points)           
     858
     859        return result
     860
     861
     862    def get_values(self, interpolation_points=None, location='vertices', indices = None):
    757863        """get values for quantity
    758864
    759865        return X, Compatible list, Numeric array (see below)
     866        interpolation_points: List of x, y coordinates where value is sought (using interpolation)
     867                If points are given, values of location and indices are ignored
    760868        location: Where values are to be stored.
    761869                  Permissible options are: vertices, edges, centroid
    762870                  and unique vertices. Default is 'vertices'
    763871
    764         In case of location == 'centroids' the dimension values must
    765         be a list of a Numerical array of length N, N being the number
    766         of elements. Otherwise it must be of dimension Nx3
    767872
    768873        The returned values with be a list the length of indices
    769         (N if indices = None).  Each value will be a list of the three
    770         vertex values for this quantity.
     874        (N if indices = None).
     875
     876        In case of location == 'centroids' the dimension of returned values will
     877        be a list or a Numerical array of length N, N being the number
     878        of elements.
     879       
     880        In case of location == 'vertices' or 'edges' the dimension of returned values will
     881        be of dimension Nx3
     882
     883        In case of location == 'unique vertices' the average value at each vertex will be
     884        returned and the dimension of returned values will be a 1d array of length "number of vertices"
     885       
    771886
    772887        Indices is the set of element ids that the operation applies to.
     
    777892        """
    778893        from Numeric import take
     894
     895        if interpolation_points is not None:
     896            return self.get_interpolated_values(interpolation_points)
     897       
     898       
    779899
    780900        if location not in ['vertices', 'centroids', 'edges', 'unique vertices']:
     
    810930                # Go through all triangle, vertex pairs
    811931                # Average the values
     932               
     933                # FIXME (Ole): Should we merge this with get_vertex_values
     934                # and use the concept of a reduction operator?
    812935                sum = 0
    813936                for triangle_id, vertex_id in triangles:
     
    9401063            precision = Float
    9411064
    942         if reduction is None:
    943             reduction = self.domain.reduction
    944 
    9451065        #Create connectivity
    9461066
    9471067        if smooth == True:
     1068           
     1069            if reduction is None:
     1070                reduction = self.domain.reduction
    9481071
    9491072            V = self.domain.get_vertices()
Note: See TracChangeset for help on using the changeset viewer.