100indexed::indexed(
const ex & b,
const symmetry &
symm,
const ex & i1,
const ex & i2,
const ex & i3,
const ex & i4) : inherited{b, i1, i2, i3, i4},
symtree(
symm)
107 seq.insert(
seq.end(), v.begin(), v.end());
113 seq.insert(
seq.end(), v.begin(), v.end());
135 inherited::read_archive(n, sym_lst);
158 inherited::archive(n);
168 if (
seq.size() > 1) {
170 auto it =
seq.begin() + 1, itend =
seq.end();
176 bool covariant =
true;
178 while (it != itend) {
180 if (
first || cur_covariant != covariant) {
184 covariant = cur_covariant;
200 while (it != itend) {
211 c.
s << openbrace <<
'(';
217 c.
s <<
')' << closebrace;
232 c.
s << std::string(level,
' ') << class_name() <<
" @" <<
this
233 << std::hex <<
", hash=0x" <<
hashvalue <<
", flags=0x" <<
flags << std::dec
234 <<
", " <<
seq.size()-1 <<
" indices"
235 <<
", symmetry=" <<
symtree << std::endl;
244 return inherited::info(inf);
254 return find_if(
seq.begin() + 1,
seq.end(),
255 [inf](
const ex & e) { return !(ex_to<idx>(e).get_value().info(inf)); }) ==
seq.end();
261 return inherited::compare_same_type(other);
266 const ex &base =
seq[0];
280 if((
typeid(*
this) ==
typeid(
indexed)) &&
seq.size()==1)
284 if (
seq.size() > 2) {
288 if (sig != std::numeric_limits<int>::max()) {
304 return real_part_function(*this).hold();
311 return imag_part_function(*this).hold();
337 ex newbase =
seq[0].expand(options);
340 for (
size_t i=0; i<newbase.
nops(); i++) {
342 s[0] = newbase.
op(i);
353 return inherited::expand(options);
372 auto it =
seq.begin() + 1, itend =
seq.end();
373 while (it != itend) {
375 throw(std::invalid_argument(
"indices of indexed object must be of type idx"));
381 throw(std::invalid_argument(
"symmetry of indexed object must be of type symmetry"));
418 if (v1.size() != v2.size())
432 exvector free_indices, dummy_indices;
434 return dummy_indices;
441 indices.insert(indices.end(), other_indices.begin(), other_indices.end());
444 return dummy_indices;
449 auto it =
seq.begin() + 1, itend =
seq.end();
450 while (it != itend) {
460 exvector free_indices, dummy_indices;
468 for (
size_t i=0; i<
nops(); i++) {
474 throw (std::runtime_error(
"add::get_free_indices: inconsistent indices in sum"));
484 for (
size_t i=0; i<
nops(); i++) {
486 un.insert(un.end(), free_indices_of_factor.begin(), free_indices_of_factor.end());
490 exvector free_indices, dummy_indices;
499 for (
size_t i=0; i<
nops(); i++) {
501 un.insert(un.end(), free_indices_of_factor.begin(), free_indices_of_factor.end());
505 exvector free_indices, dummy_indices;
519 if (
a.get_free_indices().size() ||
b.get_free_indices().size())
520 throw (std::runtime_error(
"integral::get_free_indices: boundary values should not have free indices"));
521 return f.get_free_indices();
550 if (global_size < local_size) {
554 size_t old_global_size = global_size;
555 int remaining = local_size - global_size;
556 auto it = local_dummy_indices.begin(), itend = local_dummy_indices.end();
557 while (it != itend && remaining > 0) {
559 find_if(global_dummy_indices.begin(), global_dummy_indices.end(),
560 [it](
const ex &lh) { return idx_is_equal_ignore_dim()(lh, *it); }) == global_dummy_indices.end()) {
561 global_dummy_indices.push_back(*it);
569 if (old_global_size == 0)
576 local_syms.reserve(local_size);
577 global_syms.reserve(local_size);
578 for (
size_t i=0; local_syms.size()!=local_size; i++)
580 local_syms.push_back(local_dummy_indices[i].
op(0));
582 for (
size_t i=0; global_syms.size()!=local_size; i++)
584 global_syms.push_back(global_dummy_indices[i].
op(0));
589 set_difference(local_syms.begin(), local_syms.end(), global_syms.begin(), global_syms.end(), std::back_insert_iterator<exvector>(local_uniq),
ex_is_less());
590 set_difference(global_syms.begin(), global_syms.end(), local_syms.begin(), local_syms.end(), std::back_insert_iterator<exvector>(global_uniq),
ex_is_less());
593 if (local_uniq.empty())
596 while (global_uniq.size() > local_uniq.size())
597 global_uniq.pop_back();
605 exvector::const_iterator it1, itend;
606 for (it1 = v.begin(), itend = v.end(); it1 != itend; ++it1) {
608 variant_indices.push_back(*it1);
621 bool something_changed =
false;
625 local_var_dummies.reserve(e.
nops()/2);
626 for (
size_t i=1; i<e.
nops(); ++i) {
629 for (
size_t j=i+1; j<e.
nops(); ++j) {
631 local_var_dummies.push_back(e.
op(i));
632 for (
auto k = variant_dummy_indices.begin(); k!=variant_dummy_indices.end(); ++k) {
633 if (e.
op(i).
op(0) == k->
op(0)) {
634 variant_dummy_indices.erase(k);
647 size_t numpossibs = 1 << local_var_dummies.size();
648 for (
size_t i=0; i<numpossibs; ++i) {
650 for (
size_t j=0; j<local_var_dummies.size(); ++j) {
653 ex curr_idx = local_var_dummies[j];
655 m[curr_idx] = curr_toggle;
656 m[curr_toggle] = curr_idx;
662 something_changed =
true;
674 for (
auto it2 =
seq.begin()+1, it2end =
seq.end(); it2 != it2end; ++it2) {
678 exvector::iterator vit, vitend;
679 for (vit = variant_dummy_indices.begin(), vitend = variant_dummy_indices.end(); vit != vitend; ++vit) {
680 if (it2->op(0).is_equal(vit->op(0))) {
695 something_changed =
true;
697 moved_indices.push_back(*vit);
698 variant_dummy_indices.erase(vit);
703 for (vit = moved_indices.begin(), vitend = moved_indices.end(); vit != vitend; ++vit) {
704 if (it2->op(0).is_equal(vit->op(0))) {
707 something_changed =
true;
716 if (something_changed)
719 return something_changed;
739 v.reserve(e.
nops() * 2);
744 v.push_back(e.
op(0));
745 v.push_back(e.
op(0));
747 for (
size_t i=0; i<e.
nops(); i++) {
750 v.push_back(f.
op(0));
751 v.push_back(f.
op(0));
754 non_commutative =
true;
755 for (
size_t j=0; j<f.
nops(); j++)
756 v.push_back(f.
op(j));
765 dummy_syms.reserve(r.
nops());
766 for (
auto & it : local_dummy_indices)
768 dummy_syms.push_back(it.op(0));
769 if(dummy_syms.size() < 2)
787 bool non_commutative;
791 bool something_changed =
false;
792 bool has_nonsymmetric =
false;
794 exvector::iterator it1, itend = v.end(), next_to_last = itend - 1;
795 for (it1 = v.begin(); it1 != next_to_last; it1++) {
809 exvector::iterator it2;
810 for (it2 = it1 + 1; it2 != itend; it2++) {
821 un.insert(un.end(), free1.begin(), free1.end());
826 size_t num_dummies = dummy.size();
827 if (num_dummies == 0)
831 bool contracted =
false;
832 if (free.empty() && it1->nops()==2 && it2->nops()==2) {
843 *it1 = sp.
evaluate(*it1, *it2, dim);
845 goto contraction_done;
850 contracted =
ex_to<basic>(it1->op(0)).contract_with(it1, it2, v);
855 contracted =
ex_to<basic>(it2->op(0)).contract_with(it2, it1, v);
859 if (first_noncommutative || second_noncommutative
871 ex r = (non_commutative ?
ex(
ncmul(std::move(v))) :
ex(
mul(std::move(v))));
884 something_changed =
true;
887 else if (!has_nonsymmetric &&
888 (first_nonsymmetric ||
890 has_nonsymmetric =
true;
897 exvector un, individual_dummy_indices;
898 for (it1 = v.begin(), itend = v.end(); it1 != itend; ++it1) {
903 individual_dummy_indices.insert(individual_dummy_indices.end(), dummy_indices_of_factor.begin(), dummy_indices_of_factor.end());
905 free_indices_of_factor = it1->get_free_indices();
906 un.insert(un.end(), free_indices_of_factor.begin(), free_indices_of_factor.end());
910 local_dummy_indices.insert(local_dummy_indices.end(), individual_dummy_indices.begin(), individual_dummy_indices.end());
917 if (!variant_dummy_indices.empty()) {
921 if (!non_commutative)
927 for (it1 = v.begin(), itend = v.end(); it1 != itend; ++it1) {
932 something_changed =
true;
937 if (something_changed)
938 r = non_commutative ?
ex(
ncmul(std::move(v))) :
ex(
mul(std::move(v)));
945 if (has_nonsymmetric) {
948 free_indices.clear();
953 free_indices.clear();
958 free_indices.clear();
1003 coeff = symmterm_.op(symmterm_.nops()-1);
1004 symmterm = symmterm_ / coeff;
1007 symmterm = symmterm_;
1038 for(
size_t i=0; i<x.
nops(); ++i)
1064 if (!variant_dummy_indices.empty()) {
1083 free_indices.clear();
1085 for (
size_t i=0; i<e_expanded.
nops(); i++) {
1090 free_indices = free_indices_of_term;
1095 std::ostringstream s;
1096 s <<
"simplify_indexed: inconsistent indices in sum: ";
1097 s <<
exprseq(free_indices) <<
" vs. " <<
exprseq(free_indices_of_term);
1098 throw (std::runtime_error(s.str()));
1110 free_indices.clear();
1116 if (num_terms_orig < 2 || dummy_indices.size() < 2)
1121 std::vector<terminfo> terms;
1122 for (
size_t i=0; i<sum.
nops(); i++) {
1123 const ex & term = sum.
op(i);
1125 dummy_indices_of_term.reserve(dummy_indices.size());
1126 for (
auto & i : dummy_indices)
1128 dummy_indices_of_term.push_back(i);
1134 terms.push_back(
terminfo(term, term_symm));
1141 std::vector<terminfo> terms_pass2;
1142 for (std::vector<terminfo>::const_iterator i=terms.begin(); i!=terms.end(); ) {
1145 while (j != terms.end() && j->symm == i->symm) {
1149 terms_pass2.push_back(
terminfo(i->orig * num, i->symm * num));
1154 if (terms_pass2.size() == 1)
1155 return terms_pass2[0].orig;
1158 std::vector<symminfo> sy;
1159 for (
auto & i : terms_pass2) {
1161 size_t num = i.symm.nops();
1162 for (
size_t j=0; j<num; j++)
1163 sy.push_back(
symminfo(i.symm.op(j), i.orig, num));
1165 sy.push_back(
symminfo(i.symm, i.orig, 1));
1172 std::vector<symminfo> sy_pass2;
1174 for (
auto i=sy.begin(); i!=sy.end(); ) {
1178 if (j != sy.end() && j->symmterm == i->symmterm) {
1182 while (j != sy.end() && j->symmterm == i->symmterm) {
1188 if (!
coeff.is_zero())
1189 result.push_back(
coeff * i->symmterm);
1194 sy_pass2.push_back(*i);
1201 if (sy_pass2.size() > 0) {
1206 for (std::vector<symminfo>::const_iterator i=sy_pass2.begin(); i!=sy_pass2.end(); ) {
1211 while (j != sy_pass2.end() && j->orig == i->orig) {
1216 if (num == i->num) {
1219 result.push_back(i->orig);
1224 std::vector<symminfo>::const_iterator k;
1225 for (k=i; k!=j; k++)
1226 result.push_back(k->coeff * k->symmterm);
1236 free_indices.clear();
1247 free_indices.clear();
1259 exvector free_indices, dummy_indices;
1274 exvector free_indices, dummy_indices;
1318 if (!
v1.is_equal(other.
v1))
1320 if (!
v2.is_equal(other.
v2))
1325 return dim.is_equal(other.
dim);
1330 int cmp =
v1.compare(other.
v1);
1333 cmp =
v2.compare(other.
v2);
1341 return dim.compare(other.
dim) < 0;
1346 std::cerr <<
"(" <<
v1 <<
"," <<
v2 <<
"," <<
dim <<
")";
1362 for (
auto & it1 : l)
1363 for (
auto & it2 : l)
1364 add(it1, it2, it1 * it2);
1386 std::cerr <<
"map size=" <<
spm.size() << std::endl;
1387 for (
auto & it :
spm) {
1389 std::cerr <<
"item key=";
1391 std::cerr <<
", value=" << it.second << std::endl;
1405 for (std::size_t i = 0; i < e.
nops(); ++i) {
1407 dummies.insert(dummies.end(), dummies_of_factor.begin(),
1408 dummies_of_factor.end());
1410 free_indices.insert(free_indices.begin(), free_of_factor.begin(),
1411 free_of_factor.end());
1416 dummies.insert(dummies.end(), dummy_out.begin(), dummy_out.end());
1421 for(std::size_t i = 0; i < e.
nops(); ++i) {
1423 sort(dummies_of_term.begin(), dummies_of_term.end());
1425 set_union(result.begin(), result.end(), dummies_of_term.begin(),
1426 dummies_of_term.end(), std::back_inserter<exvector>(new_vec),
1428 result.swap(new_vec);
1441 auto ip = p.begin(), ipend = p.end();
1443 while (ip != ipend) {
1446 v.insert(v.end(), v1.begin(), v1.end());
1448 while (ip1 != ipend) {
1451 v.insert(v.end(), v1.begin(), v1.end());
1464 set_intersection(va.begin(), va.end(), vb.begin(), vb.end(), std::back_insert_iterator<exvector>(common_indices),
ex_is_less());
1465 if (common_indices.empty()) {
1469 old_indices.reserve(2*common_indices.size());
1470 new_indices.reserve(2*common_indices.size());
1471 exvector::const_iterator ip = common_indices.begin(), ipend = common_indices.end();
1472 while (ip != ipend) {
1484 old_indices.push_back(*ip);
1485 new_indices.push_back(newidx);
1487 old_indices.push_back(
ex_to<varidx>(*ip).toggle_variance());
1488 new_indices.push_back(
ex_to<varidx>(newidx).toggle_variance());
1492 return lst{
lst(old_indices.begin(), old_indices.end()),
lst(new_indices.begin(), new_indices.end())};
1505 if (va.size() > 0) {
1507 if (vb.size() > 0) {
1511 if (indices_subs.
op(0).
nops() > 0)
1520 if (va.size() > 0) {
1522 if (vb.size() > 0) {
1525 if (indices_subs.
op(0).
nops() > 0) {
1530 set_difference(vb.begin(), vb.end(), indices_subs.
op(0).
begin(), indices_subs.
op(0).
end(), std::back_insert_iterator<exvector>(uncommon_indices),
ex_is_less());
1531 for (
auto & ip : uncommon_indices)
1547 return e_expanded.
map(fcn);
1554 ex result = e_expanded;
1555 for (
const auto & nu : v) {
1559 for (
int i=0; i < idim; i++) {
1564 other ==
idx(i, idim)
1567 en += result.
subs( nu.op(0) == i );
Interface to GiNaC's sums of expressions.
Archiving of GiNaC expressions.
#define GINAC_ASSERT(X)
Assertion macro for checking invariances.
exvector get_free_indices() const override
Return a vector containing the free indices of an expression.
This class stores all properties needed to record/retrieve the state of one object of class basic (or...
bool find_unsigned(const std::string &name, unsigned &ret, unsigned index=0) const
Retrieve property of type "unsigned" from node.
bool find_ex(const std::string &name, ex &ret, lst &sym_lst, unsigned index=0) const
Retrieve property of type "ex" from node.
void add_ex(const std::string &name, const ex &value)
Add property of type "ex" to node.
This class is the ABC (abstract base class) of GiNaC's class hierarchy.
unsigned hashvalue
hash value
unsigned flags
of type status_flags
virtual int compare_same_type(const basic &other) const
Returns order relation between two objects of same type.
virtual ex coeff(const ex &s, int n=1) const
Return coefficient of degree n in object s.
size_t nops() const override
ex op(size_t i) const override
Lightweight wrapper for GiNaC's symbolic objects.
ex map(map_function &f) const
const_iterator begin() const noexcept
exvector get_free_indices() const
ex expand(unsigned options=0) const
Expand an expression.
bool is_equal(const ex &other) const
ex simplify_indexed(unsigned options=0) const
Simplify/canonicalize expression containing indexed objects.
ex symmetrize_cyclic() const
Symmetrize expression by cyclic permutation over its free indices.
unsigned return_type() const
const_iterator end() const noexcept
ex subs(const exmap &m, unsigned options=0) const
int compare(const ex &other) const
ex symmetrize() const
Symmetrize expression over its free indices.
ex antisymmetrize() const
Antisymmetrize expression over its free indices.
size_t nops() const override
Number of operands/members.
ex op(size_t i) const override
Return operand/member at position i.
@ expand_indexed
expands (a+b).i to a.i+b.i
This class holds an indexed expression.
bool all_index_values_are(unsigned inf) const
Check whether all index values have a certain property.
ex thiscontainer(const exvector &v) const override
Similar to duplicate(), but with a preset sequence.
unsigned precedence() const override
Return relative operator precedence (for parenthezing output).
void printindices(const print_context &c, unsigned level) const
exvector get_free_indices() const override
Return a vector containing the free indices of an expression.
void archive(archive_node &n) const override
Save (a.k.a.
void do_print(const print_context &c, unsigned level) const
ex expand(unsigned options=0) const override
Expand expression, i.e.
void do_print_latex(const print_latex &c, unsigned level) const
void read_archive(const archive_node &n, lst &syms) override
Read (a.k.a.
void do_print_tree(const print_tree &c, unsigned level) const
ex derivative(const symbol &s) const override
Implementation of ex::diff() for an indexed object always returns 0.
bool info(unsigned inf) const override
Information about the object.
ex eval() const override
Perform automatic non-interruptive term rewriting rules.
indexed(const ex &b)
Construct indexed object with no index.
ex real_part() const override
void validate() const
Check whether all indices are of class idx and validate the symmetry tree.
ex symtree
Index symmetry (tree of symmetry objects)
exvector get_indices() const
Return a vector containing the object's indices.
exvector get_dummy_indices() const
Return a vector containing the dummy indices of the object, if any.
void print_indexed(const print_context &c, const char *openbrace, const char *closebrace, unsigned level) const
bool has_dummy_index_for(const ex &i) const
Check whether the object has an index that forms a dummy index pair with a given index.
unsigned return_type() const override
ex imag_part() const override
exvector get_free_indices() const override
Return a vector containing the free indices of an expression.
exvector get_free_indices() const override
Return a vector containing the free indices of an expression.
Non-commutative product of expressions.
exvector get_free_indices() const override
Return a vector containing the free indices of an expression.
Base class for print_contexts.
std::ostream & s
stream to output to
Context for latex-parsable output.
Context for tree-like output for debugging.
const unsigned delta_indent
size of indentation step
Helper class for storing information about known scalar products which are to be automatically replac...
bool is_defined(const ex &v1, const ex &v2, const ex &dim) const
Check whether scalar product pair is defined.
ex evaluate(const ex &v1, const ex &v2, const ex &dim) const
Return value of defined scalar product pair.
void add(const ex &v1, const ex &v2, const ex &sp)
Register scalar product pair and its value.
void clear()
Clear all registered scalar products.
void add_vectors(const lst &l, const ex &dim=wild())
Register list of vectors.
bool operator<(const spmapkey &other) const
bool operator==(const spmapkey &other) const
@ no_pattern
disable pattern matching
This class describes the symmetry of a group of indices.
bool operator()(const symminfo &si1, const symminfo &si2) const
bool operator()(const symminfo &si1, const symminfo &si2) const
This structure stores the individual symmetrized terms obtained during the simplification of sums.
ex coeff
coefficient of symmetrized term
ex symmterm
symmetrized term
size_t num
how many symmetrized terms resulted from the original term
symminfo(const ex &symmterm_, const ex &orig_, size_t num_)
bool operator()(const terminfo &ti1, const terminfo &ti2) const
This structure stores the original and symmetrized versions of terms obtained during the simplificati...
terminfo(const ex &orig_, const ex &symm_)
Interface to GiNaC's indices.
Interface to GiNaC's indexed expressions.
Interface to GiNaC's initially known functions.
Interface to GiNaC's symbolic integral.
Definition of GiNaC's lst.
Interface to symbolic matrices.
Interface to GiNaC's products of expressions.
static bool indices_consistent(const exvector &v1, const exvector &v2)
Check whether two sorted index vectors are consistent (i.e.
ex idx_symmetrization(const ex &r, const exvector &local_dummy_indices)
ex minimal_dim(const ex &dim1, const ex &dim2)
Return the minimum of two index dimensions.
const symmetry & not_symmetric()
container< std::list > lst
std::map< ex, ex, ex_is_less > exmap
B & dynallocate(Args &&... args)
Constructs a new (class basic or derived) B object on the heap.
ex symmetrize(const ex &thisex)
static void find_variant_indices(const exvector &v, exvector &variant_indices)
Given a set of indices, extract those of class varidx.
bool are_ex_trivially_equal(const ex &e1, const ex &e2)
Compare two objects of class quickly without doing a deep tree traversal.
attribute_pure const T & ex_to(const ex &e)
Return a reference to the basic-derived class T object embedded in an expression.
GINAC_IMPLEMENT_REGISTERED_CLASS_OPT_T(lst, basic, print_func< print_context >(&lst::do_print). print_func< print_tree >(&lst::do_print_tree)) template<> bool ls GINAC_BIND_UNARCHIVER)(lst)
Specialization of container::info() for lst.
bool reposition_dummy_indices(ex &e, exvector &variant_dummy_indices, exvector &moved_indices)
Raise/lower dummy indices in a single indexed objects to canonicalize their variance.
static ex rename_dummy_indices(const ex &e, exvector &global_dummy_indices, exvector &local_dummy_indices)
Rename dummy indices in an expression.
ex simplify_indexed(const ex &thisex, unsigned options=0)
bool is_dummy_pair(const idx &i1, const idx &i2)
Check whether two indices form a dummy pair.
print_func< print_context >(&varidx::do_print). print_func< print_latex >(&varidx
bool is_a(const basic &obj)
Check if obj is a T, including base classes.
ex simplify_indexed_product(const ex &e, exvector &free_indices, exvector &dummy_indices, const scalar_products &sp)
Simplify product of indexed expressions (commutative, noncommutative and simple squares),...
ex antisymmetrize(const ex &thisex)
ex op(const ex &thisex, size_t i)
void shaker_sort(It first, It last, Cmp comp, Swap swapit)
static ex symm(const ex &e, exvector::const_iterator first, exvector::const_iterator last, bool asymmetric)
int canonicalize(exvector::iterator v, const symmetry &symm)
Canonicalize the order of elements of an expression vector, according to the symmetry properties defi...
static void product_to_exvector(const ex &e, exvector &v, bool &non_commutative)
size_t number_of_type(const exvector &v)
void find_dummy_indices(const exvector &v, exvector &out_dummy)
Given a vector of indices, find the dummy indices.
bool is_exactly_a(const basic &obj)
Check if obj is a T, not including base classes.
lst rename_dummy_indices_uniquely(const exvector &va, const exvector &vb)
Similar to above, where va and vb are the same and the return value is a list of two lists for substi...
ex symmetrize_cyclic(const ex &thisex)
class_info< OPT > * class_info< OPT >::first
void find_free_and_dummy(exvector::const_iterator it, exvector::const_iterator itend, exvector &out_free, exvector &out_dummy)
Given a vector of indices, split them into two vectors, one containing the free indices,...
ex expand_dummy_sum(const ex &e, bool subs_idx)
This function returns the given expression with expanded sums for all dummy index summations,...
std::vector< ex > exvector
bool hasindex(const ex &x, const ex &sym)
exvector get_all_dummy_indices(const ex &e)
Returns all dummy indices from the exvector.
container< std::vector > exprseq
exvector get_all_dummy_indices_safely(const ex &e)
More reliable version of the form.
Interface to GiNaC's non-commutative products of expressions.
Interface to GiNaC's overloaded operators.
Interface to GiNaC's symbolic exponentiation (basis^exponent).
#define GINAC_IMPLEMENT_REGISTERED_CLASS_OPT(classname, supername, options)
Macro for inclusion in the implementation of each registered class.
Interface to relations between expressions.
bool operator()(const ex &lh, const ex &rh) const
bool operator()(const ex &lh, const ex &rh) const
bool operator()(const ex &e)
Interface to GiNaC's symbolic objects.
Interface to GiNaC's symmetry definitions.
Interface to several small and furry utilities needed within GiNaC but not of any interest to the use...