class WPHandler(object): def __init__(self): try: self.kvdb = sae.kvdb.KVClient() except: self.kvdb = Nothing() def POST(self): cur_key = const.QUOTE_PREFIX + str(time.time()+86400) #datetime.datetime.today().isoformat() handler = CGIXMLRPCRequestHandler() handler.register_introspection_functions() handler.register_instance(Mt(partial(self.kvdb.set, cur_key))) #timeout won't work return handler.handle_xmlrpc(web.data()) def GET(self): if web.input().get('del') and web.input(confirm='')['confirm']=='yes': self.kvdb.delete(web.input(_unicode=False).get('del')) if not self.kvdb.get_by_prefix(const.QUOTE_PREFIX): return 'not yet.' quotes = self.kvdb.get_by_prefix(const.QUOTE_PREFIX) body_frag = [] for q in quotes: body_frag.append('<tr><td>%s</td><td>%s</td><td><a href="?del=%s"> X </a></td></tr>' % (q[0], q[1], q[0])) body = '<table border="1px">' + ''.join(body_frag) + '</table>' web.header('Content-Type', 'text/html; charset=utf-8', unique=True) web.header('Content-Length', len(body), unique=True) return body # sae.kvdb.KVClient().delete('quotes_2012-11-20T00:57:01.754429') # cur_key = 'quotes_1353582306.66' # sae.kvdb.KVClient().delete(cur_key) # cur_key = const.QUOTE_PREFIX + '1353581051.907943' # sae.kvdb.KVClient().set(cur_key, '''<p>当年,弗里德曼的《世界是平的》对我影响最深的一句话:“你可以当会计师,可以当医生,但是不管你当什么,你都要当一个搜索引擎排名靠前者”。</p>''', time=86400)
def tail(self, t): if type(t) == TailGf: assert (self.N1, self.N2) == (t.N1, t.N2) self._singularity.copy_from (t) elif type(t) == Nothing: self._singularity = Nothing() else: raise RuntimeError, "invalid rhs for tail assignment"
def __init__(self, **d): """ The constructor have two variants : you can either provide the mesh in Matsubara frequencies yourself, or give the parameters to build it. All parameters must be given with keyword arguments. GfImFreq(indices, beta, statistic, n_points, data, tail, name) * ``indices``: a list of indices names of the block * ``beta``: Inverse Temperature * ``statistic``: 'F' or 'B' * ``positive_only``: True or False * ``n_points``: Number of Matsubara frequencies * ``data``: A numpy array of dimensions (len(indices),len(indices),n_points) representing the value of the Green function on the mesh. * ``tail``: the tail * ``name``: a name of the GF GfImFreq(indices, mesh, data, tail, name) * ``indices``: a list of indices names of the block * ``mesh``: a MeshGf object, such that mesh.TypeGF== GF_Type.Imaginary_Frequency * ``data``: A numpy array of dimensions (len(indices),len(indices),:) representing the value of the Green function on the mesh. * ``tail``: the tail * ``name``: a name of the GF .. warning:: The Green function take a **view** of the array data, and a **reference** to the tail. """ mesh = d.pop('mesh', None) if mesh is None: if 'beta' not in d: raise ValueError, "beta not provided" beta = float(d.pop('beta')) n_points = d.pop('n_points', 1025) stat = d.pop('statistic', 'F') positive_only = d.pop('positive_only', True) mesh = MeshImFreq(beta, stat, n_points, positive_only) self.dtype = numpy.complex_ indices_pack = get_indices_in_dict(d) indicesL, indicesR = indices_pack N1, N2 = len(indicesL), len(indicesR) data = d.pop('data') if 'data' in d else numpy.zeros( (len(mesh), N1, N2), self.dtype) tail = d.pop('tail') if 'tail' in d else TailGf(shape=(N1, N2)) symmetry = d.pop('symmetry', Nothing()) name = d.pop('name', 'g') assert len( d ) == 0, "Unknown parameters in GFBloc constructions %s" % d.keys() GfGeneric.__init__(self, mesh, data, tail, symmetry, indices_pack, name, GfImFreq) GfImFreq_cython.__init__(self, mesh, data, tail)
def __init__(self): try: self.kvdb = sae.kvdb.KVClient() except: self.kvdb = Nothing()
class GfGeneric: def __init__(self, mesh, data, singularity, symmetry, indices_pack, name, derived): self._mesh = mesh self._data = data self._singularity = singularity self._symmetry = symmetry self._indices_pack = indices_pack self.name = name self._derived = derived self.indicesR, self.indicesL = indices_pack copy_reg.pickle(derived, reductor, builder_cls_with_dict_arg ) @property def mesh(self): return self._mesh @property def tail(self): return self._singularity @tail.setter def tail(self, t): if type(t) == TailGf: assert (self.N1, self.N2) == (t.N1, t.N2) self._singularity.copy_from (t) elif type(t) == Nothing: self._singularity = Nothing() else: raise RuntimeError, "invalid rhs for tail assignment" @property def data(self): return self._data @data.setter def data (self, value): self._data[:,:,:] = value @property def indices(self): assert (self.indicesR == self.indicesL), "right and left indices are different" return self.indicesR @property def N1(self): return self._data.shape[1] @property def N2(self): return self._data.shape[2] #--------------------- h5 and reduction ------------------------------------------ def __reduce_to_dict__(self): return {'mesh': self._mesh, 'data': self._data, 'tail': self._singularity, 'symmetry': self._symmetry, 'indices_pack': self._indices_pack, 'name': self.name } def __write_hdf5__ (self, gr, key): self.__write_hdf5_cython__(gr, key) gr[key].create_group('indices') gr[key]['indices']['left'] = self.indicesL gr[key]['indices']['right'] = self.indicesR #gr[key]['name'] = self.name #--------------------- copies ------------------------------------------ def copy(self): return self._derived(indices_pack = self._indices_pack, mesh = self._mesh, data = self._data.copy(), tail = self._singularity.copy(), name = self.name) def copy_from(self, X): assert self._derived is X._derived assert self.mesh == X.mesh self.data = X.data self.tail = X.tail #assert list(self._indices)== list(X._indices) self._symmetry = X._symmetry self.name = X.name #--------------------- [ ] operator ------------------------------------------ def __getitem__(self, key): """Key is a tuple of index (n1, n2) as defined at construction""" if len(key) !=2: raise KeyError, "[ ] must be given two arguments" sl1, sl2 = key if type(sl1) == StringType and type(sl2) == StringType: # Convert the indices to integer indices_converter = [ IndicesConverter(self.indicesL), IndicesConverter(self.indicesR)] sl1, sl2 = [ indices_converter[i].convertToNumpyIndex(k) for i, k in enumerate(key) ] if type (sl1) != slice: sl1 = slice (sl1, sl1+1) if type (sl2) != slice: sl2 = slice (sl2, sl2+1) return self.__class__(indicesL = list(self.indicesL)[sl1], indicesR = list(self.indicesR)[sl2], name = self.name, mesh = self.mesh, data = self.data[:,sl1,sl2], tail = self.tail._make_slice(sl1, sl2)) def __setitem__(self, key, val): g = self.__getitem__(key) g <<= val #------------- Iteration ------------------------------------ def __iter__(self): for i in self.indicesL: for j in self.indicesR: b =self[i, j] b.name = "%s_%s_%s"%(self.name if hasattr(self, 'name') else '', i, j) yield i, j, b #---------------- Repr, str --------------------------------- def __str__(self): return self.name if self.name else repr(self) def __repr__(self): return """%s %s: indicesL = %s, indicesR = %s"""%(self.__class__.__name__, self.name, [x for x in self.indicesL], [x for x in self.indicesR]) #-------------- PLOT --------------------------------------- @property def real(self): """Use self.real in a plot to plot only the real part""" return PlotWrapperPartialReduce(self, RI='R') @property def imag(self): """Use self.imag in a plot to plot only the imag part""" return PlotWrapperPartialReduce(self, RI='I') #------------------ def x_data_view(self, x_window = None, flatten_y = False): """ :param x_window: the window of x variable (omega/omega_n/t/tau) for which data is requested if None, take the full window :param flatten_y: If the Green function is of size (1, 1) flatten the array as a 1d array :rtype: a tuple (X, data) where * X is a 1d numpy of the x variable inside the window requested * data is a 3d numpy array of dim (:,:, len(X)), the corresponding slice of data If flatten_y is True and dim is (1, 1, *), returns a 1d numpy """ X = [x.imag for x in self.mesh] if type(self.mesh) == MeshImFreq else [x for x in self.mesh] X, data = numpy.array(X), self.data if x_window: sl = clip_array (X, *x_window) if x_window else slice(len(X)) # the slice due to clip option x_window X, data = X[sl], data[sl,:,:] if flatten_y and data.shape[1:3]==(1, 1): data = data[:,0,0] return X, data #-------- LAZY expression system ----------------------------------------- def __lazy_expr_eval_context__(self): return LazyCTX(self) def __eq__(self, other): raise RuntimeError, " Operator not defined " def __ilshift__(self, A): """ A can be two things: * G <<= any_init will init the GFBloc with the initializer * G <<= g2 where g2 is a GFBloc will copy g2 into self """ if isinstance(A, self.__class__): if self is not A: self.copy_from(A) # otherwise it is useless AND does not work !! elif isinstance(A, lazy_expressions.LazyExpr): # A is a lazy_expression made of GF, scalars, descriptors A2= descriptors.convert_scalar_to_const(A) def e_t (x): if not isinstance(x, descriptors.Base): return x tmp = self.copy() x(tmp) return tmp self.copy_from (lazy_expressions.eval_expr_with_context(e_t, A2) ) elif isinstance(A, lazy_expressions.LazyExprTerminal): #e.g. g<<= SemiCircular (...) self <<= lazy_expressions.LazyExpr(A) elif descriptors.is_scalar(A): #in the case it is a scalar .... self <<= lazy_expressions.LazyExpr(A) else: raise RuntimeError, " <<= operator: RHS not understood" return self #-------------------- Arithmetic operations --------------------------------- def __add_iadd_impl (self, lhs, arg, is_add): d, t, rhs = lhs.data, lhs.tail,None if type(lhs) == type(arg): d[:,:,:] += arg.data t += arg.tail elif isinstance(arg, numpy.ndarray): # an array considered as a constant function MatrixStack(lhs.data).add(arg) rhs = arg elif descriptors.is_scalar(arg): # just a scalar arg = arg*numpy.identity(lhs.N1,dtype = lhs.data.dtype ) MatrixStack(lhs.data).add(arg) assert lhs.tail.shape[0] == lhs.tail.shape[1], "tail + scalar only valid in diagonal case" rhs = numpy.identity(lhs.tail.shape[0]) *arg else: raise RuntimeError, " argument type not recognized in += for %s"%arg if rhs !=None : new_tail = TailGf(shape=lhs.tail.shape) new_tail[0][:,:] = rhs if is_add : lhs._singularity = lhs.tail + new_tail else : lhs.tail = lhs.tail + new_tail return lhs def __iadd__(self, arg): return self.__add_iadd_impl(self,arg,False) def __add__(self, y): if descriptors.is_lazy(y): return lazy_expressions.make_lazy(self) + y c = self.copy() return self.__add_iadd_impl(c,y,True) def __radd__(self, y): return self.__add__(y) def __sub_isub_impl (self, lhs, arg, is_sub): d, t, rhs = lhs.data, lhs.tail,None if type(lhs) == type(arg): d[:,:,:] -= arg.data t -= arg.tail elif isinstance(arg, numpy.ndarray): # an array considered as a constant function MatrixStack(lhs.data).sub(arg) rhs = arg elif descriptors.is_scalar(arg): # just a scalar arg = arg*numpy.identity(lhs.N1,dtype = lhs.data.dtype ) MatrixStack(lhs.data).sub(arg) assert lhs.tail.shape[0] == lhs.tail.shape[1], "tail - scalar only valid in diagonal case" rhs = numpy.identity(lhs.tail.shape[0]) *arg else: raise RuntimeError, " argument type not recognized in -= for %s"%arg if rhs !=None : new_tail = TailGf(shape=lhs.tail.shape) new_tail[0][:,:] = rhs if is_sub : lhs._singularity = lhs.tail - new_tail else : lhs.tail = lhs.tail - new_tail return lhs def __isub__(self, arg): return self.__sub_isub_impl(self,arg,False) def __sub__(self, y): if descriptors.is_lazy(y): return lazy_expressions.make_lazy(self) - y c = self.copy() return self.__sub_isub_impl(c,y,True) def __rsub__(self, y): c = (-1)*self.copy() return c + y # very important to use the as +, cf above, _singularity vs tail def __imul__(self, arg): if type(self) == type(arg): d, d2 = self.data, arg.data assert d.shape == d2.shape, " Green function block multiplication with arrays of different size !" for om in range (d.shape[0]): d[om,:,:] = numpy.dot(d[om,:,:], d2[om,:,:]) self.tail = self.tail * arg.tail elif descriptors.is_scalar(arg): self.data *= arg self.tail *= arg else: raise RuntimeError, " argument type not recognized in *= for %s"%arg return self def __mul__(self, arg): if descriptors.is_lazy(arg): return lazy_expressions.make_lazy(self) * arg else: res = self.copy() res *= arg return res def __rmul__(self, arg): if descriptors.is_lazy(arg): return arg * lazy_expressions.make_lazy(self) elif descriptors.is_scalar(arg): return self.__mul__(arg) def from_L_G_R(self, L, G, R): N1 = self.data.shape[1] N2 = self.data.shape[2] assert L.shape[0] == N1 assert L.shape[1] == G.data.shape[1] assert R.shape[0] == G.data.shape[2] assert R.shape[1] == N2 MatrixStack(self.data).matmul_L_R(L, G.data, R) # this might be a bit slow t = TailGf(shape=(N1,N2)) for o in range(t.order_min, t.order_max+1): t[o] = numpy.dot(L, numpy.dot(G.tail[o], R)) self.tail = t def __idiv__(self, arg): """ If arg is a scalar, simple scalar multiplication """ if descriptors.is_lazy(arg): return lazy_expressions.make_lazy(self) / arg if descriptors.is_scalar(arg): self.data /= arg self.tail /= arg else: raise RuntimeError, " argument type not recognized in imul for %s"%arg return self def __div__(self, arg): assert descriptors.is_scalar(arg), "Error in /" res = self.copy() res /= arg return res #--------------------------------------------------- def zero(self): self <<= 0.0 #--------------------------------------------------- def invert(self): """Invert the matrix for all arguments""" MatrixStack(self.data).invert() self.tail.invert() #--------------------------------------------------- def transpose(self): """Transposes the GF Bloc: return a new transposed view""" ### WARNING: this depends on the C++ layering .... return self.__class__( indices = list(self.indices), mesh = self.mesh, data = self.data.transpose( (0, 2, 1) ), tail = self.tail.transpose(), name = self.name+'(t)') #--------------------------------------------------- def conjugate(self): """Complex conjugate of the GF Bloc. It follow the policy of numpy and make a copy only if the Green function is complex valued""" return self.__class__( indices = list(self.indices), mesh = self.mesh, data = self.data.conjugate(), tail = self.tail.conjugate(), name = self.name+'*') #------------------ Density ----------------------------------- def total_density(self): """Trace density""" return numpy.trace(self.density())
class GfGeneric: def __init__(self, mesh, data, singularity, symmetry, indices_pack, name, derived): self._mesh = mesh self._data = data self._singularity = singularity self._symmetry = symmetry self._indices_pack = indices_pack self.name = name self._derived = derived self.indicesL, self.indicesR = indices_pack copy_reg.pickle(derived, reductor, builder_cls_with_dict_arg ) @property def mesh(self): return self._mesh @property def tail(self): return self._singularity @tail.setter def tail(self, t): if type(t) == TailGf: assert (self.N1, self.N2) == (t.N1, t.N2) self._singularity.copy_from (t) elif type(t) == Nothing: self._singularity = Nothing() else: raise RuntimeError, "invalid rhs for tail assignment" @property def data(self): return self._data @data.setter def data (self, value): self._data[:,:,:] = value @property def indices(self): assert (self.indicesR == self.indicesL), "right and left indices are different" return self.indicesR @property def N1(self): return self._data.shape[1] @property def N2(self): return self._data.shape[2] #--------------------- h5 and reduction ------------------------------------------ def __reduce_to_dict__(self): return {'mesh': self._mesh, 'data': self._data, 'tail': self._singularity, 'symmetry': self._symmetry, 'indices_pack': self._indices_pack, 'name': self.name } def __write_hdf5__ (self, gr, key): self.__write_hdf5_cython__(gr, key) gr[key].create_group('indices') gr[key]['indices']['left'] = self.indicesL gr[key]['indices']['right'] = self.indicesR #gr[key]['name'] = self.name #--------------------- copies ------------------------------------------ def copy(self): return self._derived(indices_pack = self._indices_pack, mesh = self._mesh, data = self._data.copy(), tail = self._singularity.copy(), name = self.name) def copy_from(self, X): assert self._derived is X._derived assert self.mesh == X.mesh self.data = X.data self.tail = X.tail #assert list(self._indices)== list(X._indices) self._symmetry = X._symmetry self.name = X.name #--------------------- [ ] operator ------------------------------------------ def __getitem__(self, key): """Key is a tuple of index (n1, n2) as defined at construction""" if len(key) !=2: raise KeyError, "[ ] must be given two arguments" sl1, sl2 = key if type(sl1) == StringType and type(sl2) == StringType: # Convert the indices to integer indices_converter = [ IndicesConverter(self.indicesL), IndicesConverter(self.indicesR)] sl1, sl2 = [ indices_converter[i].convertToNumpyIndex(k) for i, k in enumerate(key) ] if type (sl1) != slice: sl1 = slice (sl1, sl1+1) if type (sl2) != slice: sl2 = slice (sl2, sl2+1) return self.__class__(indicesL = list(self.indicesL)[sl1], indicesR = list(self.indicesR)[sl2], name = self.name, mesh = self.mesh, data = self.data[:,sl1,sl2], tail = self.tail._make_slice(sl1, sl2)) def __setitem__(self, key, val): g = self.__getitem__(key) g <<= val #------------- Iteration ------------------------------------ def __iter__(self): for i in self.indicesL: for j in self.indicesR: b =self[i, j] b.name = "%s_%s_%s"%(self.name if hasattr(self, 'name') else '', i, j) yield i, j, b #---------------- Repr, str --------------------------------- def __str__(self): return self.name if self.name else repr(self) def __repr__(self): return """%s %s: indicesL = %s, indicesR = %s"""%(self.__class__.__name__, self.name, [x for x in self.indicesL], [x for x in self.indicesR]) #-------------- PLOT --------------------------------------- @property def real(self): """Use self.real in a plot to plot only the real part""" return PlotWrapperPartialReduce(self, RI='R') @property def imag(self): """Use self.imag in a plot to plot only the imag part""" return PlotWrapperPartialReduce(self, RI='I') #------------------ def x_data_view(self, x_window = None, flatten_y = False): """ :param x_window: the window of x variable (omega/omega_n/t/tau) for which data is requested if None, take the full window :param flatten_y: If the Green function is of size (1, 1) flatten the array as a 1d array :rtype: a tuple (X, data) where * X is a 1d numpy of the x variable inside the window requested * data is a 3d numpy array of dim (:,:, len(X)), the corresponding slice of data If flatten_y is True and dim is (1, 1, *), returns a 1d numpy """ X = [x.imag for x in self.mesh] if type(self.mesh) == MeshImFreq else [x for x in self.mesh] X, data = numpy.array(X), self.data if x_window: sl = clip_array (X, *x_window) if x_window else slice(len(X)) # the slice due to clip option x_window X, data = X[sl], data[sl,:,:] if flatten_y and data.shape[1:3]==(1, 1): data = data[:,0,0] return X, data #-------- LAZY expression system ----------------------------------------- def __lazy_expr_eval_context__(self): return LazyCTX(self) def __eq__(self, other): raise RuntimeError, " Operator not defined " def __ilshift__(self, A): """ A can be two things: * G <<= any_init will init the GFBloc with the initializer * G <<= g2 where g2 is a GFBloc will copy g2 into self """ if isinstance(A, self.__class__): if self is not A: self.copy_from(A) # otherwise it is useless AND does not work !! elif isinstance(A, lazy_expressions.LazyExpr): # A is a lazy_expression made of GF, scalars, descriptors A2= descriptors.convert_scalar_to_const(A) def e_t (x): if not isinstance(x, descriptors.Base): return x tmp = self.copy() x(tmp) return tmp self.copy_from (lazy_expressions.eval_expr_with_context(e_t, A2) ) elif isinstance(A, lazy_expressions.LazyExprTerminal): #e.g. g<<= SemiCircular (...) self <<= lazy_expressions.LazyExpr(A) elif descriptors.is_scalar(A): #in the case it is a scalar .... self <<= lazy_expressions.LazyExpr(A) else: raise RuntimeError, " <<= operator: RHS not understood" return self #-------------------- Arithmetic operations --------------------------------- def __add_iadd_impl (self, lhs, arg, is_add): d, t, rhs = lhs.data, lhs.tail,None if type(lhs) == type(arg): d[:,:,:] += arg.data t += arg.tail elif isinstance(arg, numpy.ndarray): # an array considered as a constant function MatrixStack(lhs.data).add(arg) rhs = arg elif descriptors.is_scalar(arg): # just a scalar arg = arg*numpy.identity(lhs.N1,dtype = lhs.data.dtype ) MatrixStack(lhs.data).add(arg) assert lhs.tail.shape[0] == lhs.tail.shape[1], "tail + scalar only valid in diagonal case" rhs = numpy.identity(lhs.tail.shape[0]) *arg else: raise RuntimeError, " argument type not recognized in += for %s"%arg if rhs !=None : new_tail = TailGf(shape=lhs.tail.shape) new_tail[0][:,:] = rhs if is_add : lhs._singularity = lhs.tail + new_tail else : lhs.tail = lhs.tail + new_tail return lhs def __iadd__(self, arg): return self.__add_iadd_impl(self,arg,False) def __add__(self, y): if descriptors.is_lazy(y): return lazy_expressions.make_lazy(self) + y c = self.copy() return self.__add_iadd_impl(c,y,True) def __radd__(self, y): return self.__add__(y) def __sub_isub_impl (self, lhs, arg, is_sub): d, t, rhs = lhs.data, lhs.tail,None if type(lhs) == type(arg): d[:,:,:] -= arg.data t -= arg.tail elif isinstance(arg, numpy.ndarray): # an array considered as a constant function MatrixStack(lhs.data).sub(arg) rhs = arg elif descriptors.is_scalar(arg): # just a scalar arg = arg*numpy.identity(lhs.N1,dtype = lhs.data.dtype ) MatrixStack(lhs.data).sub(arg) assert lhs.tail.shape[0] == lhs.tail.shape[1], "tail - scalar only valid in diagonal case" rhs = numpy.identity(lhs.tail.shape[0]) *arg else: raise RuntimeError, " argument type not recognized in -= for %s"%arg if rhs !=None : new_tail = TailGf(shape=lhs.tail.shape) new_tail[0][:,:] = rhs if is_sub : lhs._singularity = lhs.tail - new_tail else : lhs.tail = lhs.tail - new_tail return lhs def __isub__(self, arg): return self.__sub_isub_impl(self,arg,False) def __sub__(self, y): if descriptors.is_lazy(y): return lazy_expressions.make_lazy(self) - y c = self.copy() return self.__sub_isub_impl(c,y,True) def __rsub__(self, y): c = (-1)*self.copy() return c + y # very important to use the as +, cf above, _singularity vs tail def __imul__(self, arg): if type(self) == type(arg): d, d2 = self.data, arg.data assert d.shape == d2.shape, " Green function block multiplication with arrays of different size !" for om in range (d.shape[0]): d[om,:,:] = numpy.dot(d[om,:,:], d2[om,:,:]) self.tail = self.tail * arg.tail elif descriptors.is_scalar(arg): self.data *= arg self.tail *= arg else: raise RuntimeError, " argument type not recognized in *= for %s"%arg return self def __mul__(self, arg): if descriptors.is_lazy(arg): return lazy_expressions.make_lazy(self) * arg else: res = self.copy() res *= arg return res def __rmul__(self, arg): if descriptors.is_lazy(arg): return arg * lazy_expressions.make_lazy(self) elif descriptors.is_scalar(arg): return self.__mul__(arg) def from_L_G_R(self, L, G, R): N1 = self.data.shape[1] N2 = self.data.shape[2] assert L.shape[0] == N1 assert L.shape[1] == G.data.shape[1] assert R.shape[0] == G.data.shape[2] assert R.shape[1] == N2 MatrixStack(self.data).matmul_L_R(L, G.data, R) # this might be a bit slow for o in range(G.tail.order_min, G.tail.order_max+1): self.tail[o] = numpy.dot(L, numpy.dot(G.tail[o], R)) self.tail.mask.fill(G.tail.order_max) def __idiv__(self, arg): """ If arg is a scalar, simple scalar multiplication """ if descriptors.is_lazy(arg): return lazy_expressions.make_lazy(self) / arg if descriptors.is_scalar(arg): self.data /= arg self.tail /= arg else: raise RuntimeError, " argument type not recognized in imul for %s"%arg return self def __div__(self, arg): assert descriptors.is_scalar(arg), "Error in /" res = self.copy() res /= arg return res #--------------------------------------------------- def zero(self): self <<= 0.0 #--------------------------------------------------- def invert(self): """Invert the matrix for all arguments""" MatrixStack(self.data).invert() self.tail.invert() #--------------------------------------------------- def transpose(self): """Transposes the GF Bloc: return a new transposed view""" ### WARNING: this depends on the C++ layering .... return self.__class__( indices = list(self.indices), mesh = self.mesh, data = self.data.transpose( (0, 2, 1) ), tail = self.tail.transpose(), name = self.name+'(t)') #--------------------------------------------------- def conjugate(self): """Complex conjugate of the GF Bloc. It follow the policy of numpy and make a copy only if the Green function is complex valued""" return self.__class__( indices = list(self.indices), mesh = self.mesh, data = self.data.conjugate(), tail = self.tail.conjugate(), name = self.name+'*') #------------------ Density ----------------------------------- def total_density(self): """Trace density""" return numpy.trace(self.density())