| 560 | |
| 561 | |
| 562 | pair<string, Array<shared_ptr<CoefficientFunction>>> |
| 563 | optimize_identities(string signature, |
| 564 | const Array<shared_ptr<CoefficientFunction>>& cfs, |
| 565 | [[maybe_unused]] const map<string, bool>& options) |
| 566 | { |
| 567 | Array<shared_ptr<CoefficientFunction>> new_cfs; |
| 568 | new_cfs.SetAllocSize(cfs.Size()); |
| 569 | auto parts = split_signature(signature); |
| 570 | map<size_t, shared_ptr<CoefficientFunction>> cf_subs{}; |
| 571 | |
| 572 | // detect identity tensors that can be removed |
| 573 | Array<bool> remove(cfs.Size()); |
| 574 | remove = false; |
| 575 | for (size_t i: Range(cfs)) |
| 576 | { |
| 577 | if (dynamic_pointer_cast<IdentityCoefficientFunction>(cfs[i]) && |
| 578 | cfs[i]->Dimensions().Size() == 2) |
| 579 | { |
| 580 | if (parts[i][0] == parts[i][1] && |
| 581 | parts.back().find(parts[i][0]) == string::npos) |
| 582 | { |
| 583 | // trace of identity |
| 584 | parts[i] = parts[i][0]; |
| 585 | cf_subs[i] = ConstantCF(cfs[i]->Dimensions()[0])->Reshape(1); |
| 586 | } |
| 587 | else if (auto new_signature = substitute_id_index( |
| 588 | signature, {parts[i][0], parts[i][1]}, i, remove, true); new_signature) |
| 589 | { |
| 590 | // contraction with identity |
| 591 | signature = new_signature.value(); |
| 592 | parts = split_signature(signature); |
| 593 | remove[i] = true; |
| 594 | } |
| 595 | } |
| 596 | } |
| 597 | |
| 598 | decltype(parts) new_parts{}; |
| 599 | // remove corresponding index sets |
| 600 | for (auto i: Range(remove)) |
| 601 | if (!remove[i]) |
| 602 | new_parts.push_back(parts[i]); |
| 603 | |
| 604 | // result... |
| 605 | new_parts.push_back(parts.back()); |
| 606 | |
| 607 | // remove corresponding cfs |
| 608 | for (size_t i: Range(cfs)) |
| 609 | if (cf_subs.count(i)) |
| 610 | new_cfs.Append(cf_subs[i]); |
| 611 | else if (!remove[i]) |
| 612 | new_cfs.Append(cfs[i]); |
| 613 | |
| 614 | return {form_index_signature(new_parts), std::move(new_cfs)}; |
| 615 | } |
| 616 | |
| 617 | |
| 618 | shared_ptr<CoefficientFunction> |
no test coverage detected