def autoscale(self):
        'Try to choose the view limits intelligently'
        self.verify_intervals()
        vmin, vmax = self.dataInterval.get_bounds()

        if vmax<vmin:
            vmin, vmax = vmax, vmin

        if vmax * vmin > 0:
            raise ValueError("The interval must range from negative to positive values")

        if vmax == self.threshold:
            vmax += 1
        if vmin == -self.threshold:
            vmin -= 1

        exponent, remainder = divmod(numerix.log10(vmax - vmin), 1)

        if remainder < 0.5:
            exponent -= 1
        scale = 10**(-exponent)
        vmin = numerix.floor(scale*vmin) / scale
        vmax = numerix.ceil(scale*vmax) / scale

        return nonsingular(vmin, vmax)
    def autoscale(self):
        'Try to choose the view limits intelligently'
        self.verify_intervals()
        vmin, vmax = self.dataInterval.get_bounds()

        if vmax < vmin:
            vmin, vmax = vmax, vmin

        if vmax * vmin > 0:
            raise ValueError(
                "The interval must range from negative to positive values")

        if vmax == self.threshold:
            vmax += 1
        if vmin == -self.threshold:
            vmin -= 1

        exponent, remainder = divmod(numerix.log10(vmax - vmin), 1)

        if remainder < 0.5:
            exponent -= 1
        scale = 10**(-exponent)
        vmin = numerix.floor(scale * vmin) / scale
        vmax = numerix.ceil(scale * vmax) / scale

        return nonsingular(vmin, vmax)
Пример #3
0
    def asTrilinosMeshMatrix(self):
        """Transforms a Pysparse matrix into a Trilinos matrix

        Maintains the Trilinos matrix as an attribute.

        Returns
        -------
        ~fipy.matrices.trilinosMatrix._TrilinosMatrix
        """
        A = self.matrix.copy()
        values, irow, jcol = A.find()

        if not hasattr(self, 'trilinosMatrix'):
            if A.shape[0] == 0:
                bandwidth = 0
            else:
                bandwidth = int(numerix.ceil(float(len(values)) / float(A.shape[0])))
            bandwidth = 1
            from fipy.matrices.trilinosMatrix import _TrilinosMeshMatrixKeepStencil
            tmp = _TrilinosMeshMatrixKeepStencil(mesh=self.mesh, bandwidth=bandwidth,
                                                 numberOfVariables=self.numberOfVariables,
                                                 numberOfEquations=self.numberOfEquations)
            self.trilinosMatrix = tmp

        self.trilinosMatrix.addAt(values, irow, jcol)
        self.trilinosMatrix.finalize()

        return self.trilinosMatrix
Пример #4
0
    def asTrilinosMeshMatrix(self):
        """Transforms a pysparse matrix into a trilinos matrix and maintains the
        trilinos matrix as an attribute.

        :Returns:
          The trilinos matrix.

        """
        A = self.matrix.copy()
        values, irow, jcol = A.find()

        if not hasattr(self, 'trilinosMatrix'):
            if A.shape[0] == 0:
                bandwidth = 0
            else:
                bandwidth = int(numerix.ceil(float(len(values)) / float(A.shape[0])))
            bandwidth = 1
            from fipy.matrices.trilinosMatrix import _TrilinosMeshMatrixKeepStencil
            self.trilinosMatrix = _TrilinosMeshMatrixKeepStencil(mesh=self.mesh, bandwidth=bandwidth,
                                                                 numberOfVariables=self.numberOfVariables,
                                                                 numberOfEquations=self.numberOfEquations)

        self.trilinosMatrix.addAt(values, irow, jcol)
        self.trilinosMatrix.finalize()

        return self.trilinosMatrix
    def __call__(self):
        'Return the locations of the ticks'
        b = self._base

        vmin, vmax = self.axis.get_view_interval()

        if vmax < vmin:
            vmin, vmax = vmax, vmin

        if vmax * vmin > 0:
            raise ValueError(
                "The interval must range from negative to positive values")

        ticklocs = []

        for limit, sgn in zip([vmax, -vmin], [1, -1]):
            numdec = numerix.floor(limit + self.threshold) - numerix.ceil(
                self.threshold)

            if self._subs is None:  # autosub
                if numdec > 10:
                    subs = numerix.array([1.0])
                elif numdec > 6:
                    subs = numerix.arange(2.0, b, 2.0)
                else:
                    subs = numerix.arange(2.0, b)
                subs = numerix.log(subs) / numerix.log(b)
            else:
                subs = self._subs
                if numdec == 0 and len(subs) == 1:
                    subs = numerix.array(
                        list(subs) + list(
                            numerix.log(numerix.arange(2.0, b)) /
                            numerix.log(b)))

            stride = 1
            while numdec // stride + 1 > self.numticks:
                stride += 1

            for decadeStart in numerix.arange(
                    numerix.floor(self.threshold),
                    numerix.ceil(limit + self.threshold) + stride, stride):
                ticks = subs + decadeStart - self.threshold
                ticklocs.extend(sgn * ticks.compress(ticks > 0))

        return numerix.array(ticklocs)
    def __call__(self):
        'Return the locations of the ticks'
        b=self._base

        vmin, vmax = self.axis.get_view_interval()

        if vmax<vmin:
            vmin, vmax = vmax, vmin

        if vmax * vmin > 0:
            raise ValueError("The interval must range from negative to positive values")

        ticklocs = []

        for limit, sgn in zip([vmax, -vmin], [1, -1]):
            numdec = numerix.floor(limit+self.threshold)-numerix.ceil(self.threshold)

            if self._subs is None: # autosub
                if numdec>10:
                    subs = numerix.array([1.0])
                elif numdec>6:
                    subs = numerix.arange(2.0, b, 2.0)
                else:
                    subs = numerix.arange(2.0, b)
                subs = numerix.log(subs) / numerix.log(b)
            else:
                subs = self._subs
                if numdec == 0 and len(subs) == 1:
                    subs = numerix.array(list(subs) + list(numerix.log(numerix.arange(2.0, b)) / numerix.log(b)))

            stride = 1
            while numdec // stride + 1 > self.numticks:
                stride += 1

            for decadeStart in numerix.arange(numerix.floor(self.threshold),
                                              numerix.ceil(limit + self.threshold)+stride,
                                              stride):
                ticks = subs + decadeStart - self.threshold
                ticklocs.extend( sgn * ticks.compress(ticks > 0) )

        return numerix.array(ticklocs)
    def plot(self, matrix, RHSvector, log='auto'):
        import tempfile
        import os

        if "print" in os.environ['FIPY_DISPLAY_MATRIX'].lower().split():
            print("-" * 75)
            print(self.title)
            print("-" * 75)
            print("L:")
            print(matrix)
            print("b:", RHSvector)

        (f, mtxName) = tempfile.mkstemp(suffix='.mtx')
        matrix.exportMmf(mtxName)
        mtx = mmio.mmread(mtxName)
        os.remove(mtxName)

        pyplot.ion()

        c = mtx.tocoo()
        y = c.row
        x = c.col
        z = c.data
        N = matrix._shape[0]

        b = RHSvector
        if numerix.shape(b) == ():
            b = numerix.zeros((N, ), 'l')

        if len(z) == 0:
            y = numerix.zeros((1, ), 'l')
            x = numerix.zeros((1, ), 'l')
            z = numerix.zeros((1, ), 'l')

        def signed_to_logs(v):
            return (numerix.where(v > 0, numerix.log10(v), numerix.nan),
                    numerix.where(v < 0, numerix.log10(-v), numerix.nan))

        def logs_to_signed(v, plus, minus):
            v = numerix.where(v > 0, plus, -minus)
            v = numerix.where(numerix.isnan(v), 0., v)

            return v

        zPlus, zMinus = signed_to_logs(z)
        bPlus, bMinus = signed_to_logs(b)

        logs = (zPlus, zMinus, bPlus, bMinus)

        log = ((log == True)
               or (log == 'auto' and
                   (numerix.nanmax(numerix.concatenate(logs)) -
                    numerix.nanmin(numerix.concatenate(logs)) > 2)))

        if log:
            zMin = numerix.nanmin(numerix.concatenate(logs))
            zMax = numerix.nanmax(numerix.concatenate(logs))

            zMin -= 0.5

            numdec = numerix.floor(zMax) - numerix.ceil(zMin)
            if numdec < 0:
                zMax += 0.5

            for v in logs:
                v -= zMin

            zRange = zMax - zMin

            if zRange == 0:
                zRange = numerix.nanmax(zPlus) + 1

            z = logs_to_signed(z, zPlus, zMinus)
            b = logs_to_signed(b, bPlus, bMinus)

            fmt = SignedLogFormatter(threshold=zMin)
            loc = SignedLogLocator(threshold=zMin)

        else:
            zRange = max(abs(numerix.concatenate((z, b))))

            if zRange == 0:
                zRange = 1

            fmt = None
            loc = None

        pyplot.ioff()

        fig = pyplot.figure(self.id)
        fig.clf()

        usetex = rcParams['text.usetex']
        rcParams['text.usetex'] = False

        cmap = cm.RdBu

        norm = Normalize(vmin=-zRange, vmax=zRange)

        x0 = self.margin
        L_ax = fig.add_axes([
            x0 / self.aspect, self.margin, self.L_width / self.aspect,
            self.L_width
        ])
        L_ax.text(0.5,
                  -0.1,
                  "L",
                  transform=L_ax.transAxes,
                  horizontalalignment='center',
                  verticalalignment='baseline')

        x0 += self.L_width + self.buffer
        c_ax = fig.add_axes([
            x0 / self.aspect, self.margin, self.c_width / self.aspect,
            self.L_width
        ])

        x0 += self.c_width + self.buffer
        b_ax = fig.add_axes([
            x0 / self.aspect, self.margin, self.b_width / self.aspect,
            self.L_width
        ],
                            sharey=L_ax)
        b_ax.text(0.5,
                  -0.1,
                  "b",
                  transform=b_ax.transAxes,
                  horizontalalignment='center',
                  verticalalignment='baseline')

        def scatterRectangles(x, y, z, norm=None, cmap=None):
            patches = [
                Rectangle(numerix.array([X - 0.5, Y - 0.5]),
                          1.,
                          1.,
                          edgecolor='none') for X, Y in zip(x, y)
            ]

            collection = PatchCollection(patches,
                                         norm=norm,
                                         cmap=cmap,
                                         edgecolors='none')
            collection.set_array(z)

            return collection

        L_ax.add_collection(
            scatterRectangles(x=x, y=y, z=z, norm=norm, cmap=cmap))

        b_ax.add_collection(
            scatterRectangles(x=numerix.zeros((N, ), 'l'),
                              y=numerix.arange(N),
                              z=b,
                              norm=norm,
                              cmap=cmap))

        ColorbarBase(ax=c_ax,
                     cmap=cmap,
                     norm=norm,
                     orientation='vertical',
                     format=fmt,
                     ticks=loc)

        pyplot.setp((b_ax.get_xticklabels(), b_ax.get_yticklabels(),
                     b_ax.get_xticklines(), b_ax.get_yticklines()),
                    visible=False)

        L_ax.set_xlim(xmin=-0.5, xmax=N - 0.5)
        L_ax.set_ylim(ymax=-0.5, ymin=N - 0.5)

        b_ax.set_xlim(xmin=-0.5, xmax=0.5)
        b_ax.set_ylim(ymax=-0.5, ymin=N - 0.5)

        fig.suptitle(self.title, x=0.5, y=0.95, fontsize=14)

        pyplot.draw()

        rcParams['text.usetex'] = usetex
Пример #8
0
 def ceil(self):
     return self._UnaryOperatorVariable(lambda a: numerix.ceil(a))
    def plot(self, matrix, RHSvector, log='auto'):
        import tempfile
        import os

        if "print" in os.environ['FIPY_DISPLAY_MATRIX'].lower().split():
            print("-"*75)
            print(self.title)
            print("-"*75)
            print("L:")
            print(matrix)
            print("b:", RHSvector)

        (f, mtxName) = tempfile.mkstemp(suffix='.mtx')
        matrix.exportMmf(mtxName)
        mtx = mmio.mmread(mtxName)
        os.remove(mtxName)

        pyplot.ion()

        c = mtx.tocoo()
        y = c.row
        x = c.col
        z = c.data
        N = matrix._shape[0]

        b = RHSvector
        if numerix.shape(b) == ():
            b = numerix.zeros((N,), 'l')

        if len(z) == 0:
            y = numerix.zeros((1,), 'l')
            x = numerix.zeros((1,), 'l')
            z = numerix.zeros((1,), 'l')

        def signed_to_logs(v):
            return (numerix.where(v > 0, numerix.log10(v), numerix.nan),
                    numerix.where(v < 0, numerix.log10(-v), numerix.nan))

        def logs_to_signed(v, plus, minus):
            v = numerix.where(v > 0, plus, -minus)
            v = numerix.where(numerix.isnan(v), 0., v)

            return v

        zPlus, zMinus = signed_to_logs(z)
        bPlus, bMinus = signed_to_logs(b)

        logs = (zPlus, zMinus, bPlus, bMinus)

        log = ((log == True)
               or (log == 'auto'
                   and (numerix.nanmax(numerix.concatenate(logs))
                        - numerix.nanmin(numerix.concatenate(logs)) > 2)))

        if log:
            zMin = numerix.nanmin(numerix.concatenate(logs))
            zMax = numerix.nanmax(numerix.concatenate(logs))

            zMin -= 0.5

            numdec = numerix.floor(zMax) - numerix.ceil(zMin)
            if numdec < 0:
                zMax += 0.5

            for v in logs:
                v -= zMin

            zRange = zMax - zMin

            if zRange == 0:
                zRange = numerix.nanmax(zPlus) + 1

            z = logs_to_signed(z, zPlus, zMinus)
            b = logs_to_signed(b, bPlus, bMinus)

            fmt = SignedLogFormatter(threshold=zMin)
            loc = SignedLogLocator(threshold=zMin)

        else:
            zRange = max(abs(numerix.concatenate((z, b))))

            if zRange == 0:
                zRange = 1

            fmt = None
            loc = None


        pyplot.ioff()

        fig = pyplot.figure(self.id)
        fig.clf()

        usetex = rcParams['text.usetex']
        rcParams['text.usetex'] = False

        cmap = cm.RdBu

        norm = Normalize(vmin=-zRange, vmax=zRange)

        x0 = self.margin
        L_ax = fig.add_axes([x0 / self.aspect, self.margin, self.L_width / self.aspect, self.L_width])
        L_ax.text(0.5, -0.1, "L",
                  transform=L_ax.transAxes, horizontalalignment='center', verticalalignment='baseline')

        x0 += self.L_width + self.buffer
        c_ax = fig.add_axes([x0 / self.aspect, self.margin, self.c_width / self.aspect, self.L_width])

        x0 += self.c_width + self.buffer
        b_ax = fig.add_axes([x0 / self.aspect, self.margin, self.b_width / self.aspect, self.L_width],
                            sharey=L_ax)
        b_ax.text(0.5, -0.1, "b",
                  transform=b_ax.transAxes, horizontalalignment='center', verticalalignment='baseline')



        def scatterRectangles(x, y, z, norm=None, cmap=None):
            patches = [Rectangle(numerix.array([X - 0.5, Y - 0.5]), 1., 1.,
                                 edgecolor='none') for X, Y in zip(x, y)]

            collection = PatchCollection(patches, norm=norm, cmap=cmap,
                                         edgecolors='none')
            collection.set_array(z)

            return collection

        L_ax.add_collection(scatterRectangles(x=x, y=y, z=z,
                                              norm=norm, cmap=cmap))

        b_ax.add_collection(scatterRectangles(x=numerix.zeros((N,), 'l'), y=numerix.arange(N), z=b,
                                              norm=norm, cmap=cmap))

        ColorbarBase(ax=c_ax, cmap=cmap, norm=norm, orientation='vertical',
                     format=fmt, ticks=loc)

        pyplot.setp((b_ax.get_xticklabels(),
                     b_ax.get_yticklabels(),
                     b_ax.get_xticklines(),
                     b_ax.get_yticklines()), visible=False)

        L_ax.set_xlim(xmin=-0.5, xmax=N-0.5)
        L_ax.set_ylim(ymax=-0.5, ymin=N-0.5)

        b_ax.set_xlim(xmin=-0.5, xmax=0.5)
        b_ax.set_ylim(ymax=-0.5, ymin=N-0.5)

        fig.suptitle(self.title, x=0.5, y=0.95, fontsize=14)

        pyplot.draw()

        rcParams['text.usetex'] = usetex
Пример #10
0
    def update_artists(self, tidx):
        """
        Update the data of the line artists for time point

        Args:
            tidx (int): The time index

        """
        self.logger.info(
            'Updating artist_paths for time step #{}'.format(tidx))

        clocktime = self.model.times[tidx]
        dt = int(np.ceil((clocktime - self._clock).numericValue))
        H, M, S = [int(s.value) for s in clocktime.inUnitsOf('h', 'min', 's')]
        hmstr = self.clockstr.format(H, M, S, dt)
        self._clock = clocktime

        self.clock_artist.set_text(hmstr)
        self.logger.debug('Time: {}'.format(hmstr))

        # self.axes_all
        # all_depth_axes = itertools.chain(self.axes_depth, self.axes_depth_linked.values())
        # all_time_axes = itertools.chain(self.axes_time, self.axes_time_linked.values())

        for artist, dpath in self.artist_paths.items():

            ax = artist.axes
            self.logger.info('Updating {} artist {} from {}'.format(
                ax.name, artist, dpath))

            # get the data
            data = self.model.get_data(dpath, tidx=tidx)
            data_unit = data.unit.name()
            self.logger.debug('Got data {} {} of unit: {!r}'.format(
                data.__class__.__name__, data.shape, data_unit))

            # cast to units
            if not getattr(ax, 'data_unit_', None):
                ax.data_unit_ = data.unit.name()
                self.logger.debug('Set axes {} to unit: {}'.format(
                    ax.name, ax.data_unit_))
                # if ax in all_time_axes:
                #     ax.set_ylabel(ax.data_unit_)
            ax_unit = ax.data_unit_

            try:
                D = data.inUnitsOf(ax_unit).value
                self.logger.debug('Got data {} dtype {} --> {}'.format(
                    D.dtype, D.min(), D.max()))

            except TypeError:
                self.logger.error(
                    "Error casting {} units from {} to {}".format(
                        dpath, data_unit, ax_unit))
                # raise
                D = data.value

            # now data D is a numpy array

            label_base = self._get_label(dpath)

            # normalize if necessary
            data_normed = getattr(ax, 'data_normed_', False)

            if data_normed:
                Dabs = abs(D)
                Dabsmax = float(Dabs.max())
                Dabsmin = float(Dabs.min())
                Drange = Dabsmax - Dabsmin
                if Drange <= 1e-15:
                    self.logger.debug('abs(data) max = min = {:.2g}'.format(
                        Dabsmax, Dabsmin))
                    if Dabsmax == 0.0:
                        Drange = 1.0
                        self.logger.debug(
                            'all data is zero, normalizing by 1.0')
                    else:
                        Drange = Dabsmax
                        self.logger.debug(
                            'normalizing by abs(data).max = {:.2g}'.format(
                                Dabsmax))
                else:
                    self.logger.debug(
                        'abs(data) range {:.2g} --> {:.2g}'.format(
                            Dabsmin, Dabsmax))
                    Drange = Dabsmax

                D = D / Drange

                self.logger.info(
                    'Normalized {} data by {:.3g}: {:.3g} --> {:.3g}'.format(
                        label_base, Drange, D.min(), D.max()))

                label = label_base + flabel(Drange)

                if D.max() > 1.01:
                    self.logger.error('data max {} is not <=1.01'.format(
                        D.max()))
                    self.logger.warning(D)
                    self.logger.warning('Drange: {}'.format(Drange))
                    self.logger.warning('Original data: {}'.format(
                        data.inUnitsOf(ax_unit).value))
                    raise RuntimeError(
                        'Data normalization of {} failed!'.format(dpath))

            else:
                label = label_base

            # now ready to set data and label
            if ax in self.axes_depth_all:
                artist.set_xdata(D)
                artist.set_label(label)

            elif ax in self.axes_time_all:
                xdata, ydata = artist.get_data()
                t = self.model.get_data('/time', tidx=tidx)
                artist.set_xdata(np.append(xdata, t.inUnitsOf('h').value))
                artist.set_ydata(np.append(ydata, D))
                artist.set_label(label + ' {}'.format(ax.data_unit_))

            self.logger.debug('{} updated'.format(artist))

        self.update_legends()

        for ax in self.axes_depth + self.axes_time:
            ax.relim()
            ax.autoscale_view(scalex=True, scaley=True)