Arcane  4.2.3.0
Developer documentation
Loading...
Searching...
No Matches
IncrementalItemConnectivity.cc
1// -*- tab-width: 2; indent-tabs-mode: nil; coding: utf-8-with-signature -*-
2//-----------------------------------------------------------------------------
3// Copyright 2000-2026 CEA (www.cea.fr) IFPEN (www.ifpenergiesnouvelles.com)
4// See the top-level COPYRIGHT file for details.
5// SPDX-License-Identifier: Apache-2.0
6//-----------------------------------------------------------------------------
7/*---------------------------------------------------------------------------*/
8/* IncrementalItemConnectivity.cc (C) 2000-2024 */
9/* */
10/* Incremental connectivity of entities. */
11/*---------------------------------------------------------------------------*/
12/*---------------------------------------------------------------------------*/
13
14#include "arcane/mesh/IncrementalItemConnectivity.h"
15
16#include "arcane/utils/StringBuilder.h"
17#include "arcane/utils/ArgumentException.h"
18#include "arcane/utils/PlatformUtils.h"
19#include "arcane/utils/ValueConvert.h"
20
21#include "arcane/core/IMesh.h"
22#include "arcane/core/IItemFamily.h"
23#include "arcane/core/ConnectivityItemVector.h"
25#include "arcane/core/ObserverPool.h"
26#include "arcane/core/Properties.h"
27#include "arcane/core/IndexedItemConnectivityView.h"
28#include "arcane/core/internal/IDataInternal.h"
29#include "arcane/core/internal/IItemFamilyInternal.h"
30#include "arcane/core/internal/IIncrementalItemConnectivityInternal.h"
31
32#include "arcane/mesh/IndexedItemConnectivityAccessor.h"
33#include "arcane/mesh/internal/LazyMemoryPool.h"
34
35/*---------------------------------------------------------------------------*/
36/*---------------------------------------------------------------------------*/
37
38namespace Arcane::mesh
39{
40
41/*---------------------------------------------------------------------------*/
42/*---------------------------------------------------------------------------*/
43
44IndexedItemConnectivityAccessor::
45IndexedItemConnectivityAccessor(IndexedItemConnectivityViewBase view, IItemFamily* target_item_family)
46: IndexedItemConnectivityViewBase(view)
47, m_item_shared_info(target_item_family->_internalApi()->commonItemSharedInfo())
48{}
49
50/*---------------------------------------------------------------------------*/
51/*---------------------------------------------------------------------------*/
52
53IndexedItemConnectivityAccessor::
54IndexedItemConnectivityAccessor(IIncrementalItemConnectivity* connectivity)
55: m_item_shared_info(connectivity->targetFamily()->_internalApi()->commonItemSharedInfo())
56{
57 auto* ptr = dynamic_cast<mesh::IncrementalItemConnectivityBase*>(connectivity);
58 if (ptr)
59 IndexedItemConnectivityViewBase::set(ptr->connectivityView());
60}
61
62/*---------------------------------------------------------------------------*/
63/*---------------------------------------------------------------------------*/
64
65AbstractIncrementalItemConnectivity::
66AbstractIncrementalItemConnectivity(IItemFamily* source_family,
67 IItemFamily* target_family,
68 const String& connectivity_name)
69: TraceAccessor(source_family->traceMng())
70, m_source_family(source_family)
71, m_target_family(target_family)
72, m_name(connectivity_name)
73{
74 m_families.add(m_source_family);
75 m_families.add(m_target_family);
76
77 //TODO: these references must be removed upon destruction.
78 source_family->_internalApi()->addSourceConnectivity(this);
79 target_family->_internalApi()->addTargetConnectivity(this);
80}
81
82/*---------------------------------------------------------------------------*/
83/*---------------------------------------------------------------------------*/
84
85Ref<IIncrementalItemSourceConnectivity> AbstractIncrementalItemConnectivity::
86toSourceReference()
87{
89}
90
91/*---------------------------------------------------------------------------*/
92/*---------------------------------------------------------------------------*/
93
94Ref<IIncrementalItemTargetConnectivity> AbstractIncrementalItemConnectivity::
95toTargetReference()
96{
98}
99
100/*---------------------------------------------------------------------------*/
101/*---------------------------------------------------------------------------*/
102
103/*---------------------------------------------------------------------------*/
104/*---------------------------------------------------------------------------*/
105
106class IncrementalItemConnectivityContainer
107{
108 public:
109
110 IncrementalItemConnectivityContainer(IMesh* mesh, const String& var_name)
111 : m_var_name(var_name)
112 , m_connectivity_nb_item_variable(VariableBuildInfo(mesh, var_name + "Nb", IVariable::PPrivate))
113 , m_connectivity_index_variable(VariableBuildInfo(mesh, var_name + "Index", IVariable::PPrivate))
114 , m_connectivity_list_variable(VariableBuildInfo(mesh, var_name + "List", IVariable::PPrivate))
115 , m_connectivity_nb_item_array(m_connectivity_nb_item_variable._internalTrueData()->_internalDeprecatedValue())
116 , m_connectivity_index_array(m_connectivity_index_variable._internalTrueData()->_internalDeprecatedValue())
117 , m_connectivity_list_array(m_connectivity_list_variable._internalTrueData()->_internalDeprecatedValue())
118 {
119 // Adds a tag to indicate that these variables are associated with connectivity.
120 // For now, this is only used for display statistics.
121
122 String tag_name = "ArcaneConnectivity";
123 m_connectivity_nb_item_variable.addTag(tag_name, "1");
124 m_connectivity_index_variable.addTag(tag_name, "1");
125 m_connectivity_list_variable.addTag(tag_name, "1");
126 }
127
128 String m_var_name;
129
130 VariableArrayInt32 m_connectivity_nb_item_variable;
131 VariableArrayInt32 m_connectivity_index_variable;
132 VariableArrayInt32 m_connectivity_list_variable;
133
134 VariableArrayInt32::ContainerType& m_connectivity_nb_item_array;
135 VariableArrayInt32::ContainerType& m_connectivity_index_array;
136 VariableArrayInt32::ContainerType& m_connectivity_list_array;
137
138 ObserverPool m_observers;
139
148
149 public:
150
151 Integer size() const { return m_connectivity_nb_item_array.size(); }
152
153 bool isAllocated() const { return size() > 0; }
154
155 void _checkResize(Int32 lid)
156 {
157 //TODO: reuse the code from ItemFamily::_setUniqueId().
158 Integer size = m_connectivity_nb_item_array.size();
159 Integer wanted_size = lid + 1;
160 if (wanted_size < size)
161 return;
162 Integer capacity = m_connectivity_nb_item_array.capacity();
163 if (wanted_size < capacity) {
164 // No need to increase capacity.
165 }
166 else {
167 Integer reserve_size = 1000;
168 while (lid > reserve_size) {
169 reserve_size *= 2;
170 }
171 m_connectivity_nb_item_array.reserve(reserve_size);
172 m_connectivity_index_array.reserve(reserve_size);
173 }
174 m_connectivity_nb_item_array.resize(wanted_size);
175 m_connectivity_index_array.resize(wanted_size);
176 }
177
178 void reserveForItems(Int32 capacity)
179 {
180 m_connectivity_nb_item_array.reserve(capacity);
181 m_connectivity_index_array.reserve(capacity);
182 }
183
184 public:
185
215
216 public:
217};
218
220
221/*---------------------------------------------------------------------------*/
222/*---------------------------------------------------------------------------*/
223
226{
227 public:
228
229 explicit InternalApi(IncrementalItemConnectivityBase* v)
230 : m_internal_api(v)
231 {}
232
233 public:
234
235 void shrinkMemory() override { return m_internal_api->_shrinkMemory(); }
237 {
238 m_internal_api->_addMemoryInfos(mem_info);
239 }
240 void notifyEndUpdateFromMesh() override { m_internal_api->_trimLazyViews(); }
241
242 private:
243
244 IncrementalItemConnectivityBase* m_internal_api = nullptr;
245};
246
247/*---------------------------------------------------------------------------*/
248/*---------------------------------------------------------------------------*/
249
250IncrementalItemConnectivityBase::
251IncrementalItemConnectivityBase(IItemFamily* source_family, IItemFamily* target_family,
252 const String& aname)
253: AbstractIncrementalItemConnectivity(source_family, target_family, aname)
254, m_internal_api(std::make_unique<InternalApi>(this))
255{
256 StringBuilder var_name("Connectivity");
257 var_name += aname;
258 var_name += source_family->name();
259 var_name += target_family->name();
260
261 IMesh* mesh = source_family->mesh();
262 m_p = new IncrementalItemConnectivityContainer(mesh, var_name);
263
264 using ThatClass = IncrementalItemConnectivityBase;
265 // Get read events to indicate that the views must be updated.
266 m_p->m_observers.addObserver(this, &ThatClass::_notifyConnectivityNbItemChangedFromObservable,
267 m_p->m_connectivity_nb_item_variable.variable()->readObservable());
268
269 m_p->m_observers.addObserver(this, &ThatClass::_notifyConnectivityIndexChanged,
270 m_p->m_connectivity_index_variable.variable()->readObservable());
271
272 m_p->m_observers.addObserver(this, &ThatClass::_notifyConnectivityListChanged,
273 m_p->m_connectivity_list_variable.variable()->readObservable());
274
275 // A protection must hold the per-source arrays themselves, so that a run
276 // without the lazy state can read it back: leave that state just before
277 // either variable is written.
278 m_p->m_observers.addObserver(this, &ThatClass::_checkMaterialize,
279 m_p->m_connectivity_nb_item_variable.variable()->writeObservable());
280 m_p->m_observers.addObserver(this, &ThatClass::_checkMaterialize,
281 m_p->m_connectivity_index_variable.variable()->writeObservable());
282
283 // Update the views from the associated arrays.
284 // This must be done whenever the size of an array changes because then
285 // the array might be reallocated and thus the associated view might become invalid.
286 _notifyConnectivityListChanged();
287 _notifyConnectivityIndexChanged();
289}
290
291/*---------------------------------------------------------------------------*/
292/*---------------------------------------------------------------------------*/
293
294IncrementalItemConnectivityBase::
295~IncrementalItemConnectivityBase()
296{
297 delete m_p;
298}
299
300/*---------------------------------------------------------------------------*/
301/*---------------------------------------------------------------------------*/
302
304reserveMemoryForNbSourceItems(Int32 n, bool pre_alloc_connectivity)
305{
306 if (n <= 0)
307 return;
308
309 if (!m_is_lazy)
310 m_p->reserveForItems(n);
311 _notifyConnectivityIndexChanged();
312 _notifyConnectivityNbItemChanged();
313
314 if (pre_alloc_connectivity) {
315 Int32 pre_alloc_size = preAllocatedSize();
316 if (pre_alloc_size > 0) {
317 m_p->m_connectivity_list_array.reserve(n * pre_alloc_size);
318 _notifyConnectivityListChanged();
319 }
320 }
321}
322
323/*---------------------------------------------------------------------------*/
324/*---------------------------------------------------------------------------*/
325
326void IncrementalItemConnectivityBase::
327_notifyConnectivityListChanged()
328{
329 m_connectivity_list = m_p->m_connectivity_list_array.view();
330 if (m_item_connectivity_list)
331 m_item_connectivity_list->_setConnectivityList(m_item_connectivity_index, m_connectivity_list);
332}
333
334/*---------------------------------------------------------------------------*/
335/*---------------------------------------------------------------------------*/
336
337void IncrementalItemConnectivityBase::
338_lazyNotifySourceItemAdded(Int32 lid)
339{
340 Int32 n = lid + 1;
341 if (n > m_p->m_lazy_nb_source)
342 m_p->m_lazy_nb_source = n;
343 if (n <= m_connectivity_nb_item.size())
344 return; // the published views still cover this localId
346}
347
348/*---------------------------------------------------------------------------*/
349/*---------------------------------------------------------------------------*/
355_publishLazyViews(Int32 nb_source)
356{
357 // The views span the whole buffer rather than the source items seen so far, so
358 // they are republished only when one is outgrown. Announcing more than the item
359 // count is safe here: every reader indexes the view by a local id below that
360 // count, and a bounds check that passes on a longer view would have passed on
361 // the exact one.
362 ConstArrayView<Int32> zeros = IncrementalItemConnectivityContainer::m_lazy_pool.grow(m_p->m_lazy_buffer, nb_source);
363 _setLazyViews(zeros);
364}
365
366/*---------------------------------------------------------------------------*/
367/*---------------------------------------------------------------------------*/
368
369void IncrementalItemConnectivityBase::
370_setLazyViews(ConstArrayView<Int32> zeros)
371{
372 Int32* data = const_cast<Int32*>(zeros.data());
373 m_connectivity_index = Int32ArrayView(zeros.size(), data);
374 m_connectivity_nb_item = Int32ArrayView(zeros.size(), data);
375 if (m_item_connectivity_list) {
376 m_item_connectivity_list->_setConnectivityIndex(m_item_connectivity_index, m_connectivity_index);
377 m_item_connectivity_list->_setConnectivityNbItem(m_item_connectivity_index, m_connectivity_nb_item);
378 }
379}
380
381/*---------------------------------------------------------------------------*/
382/*---------------------------------------------------------------------------*/
392{
393 if (!m_is_lazy)
394 return;
395 Int32 nb_zero = m_p->m_lazy_nb_source;
396 for (IItemFamily* family : _sourceFamily()->mesh()->itemFamilies())
397 nb_zero = math::max(nb_zero, family->maxLocalId());
398 _setLazyViews(IncrementalItemConnectivityContainer::m_lazy_pool.trim(m_p->m_lazy_buffer, nb_zero));
399}
400
401/*---------------------------------------------------------------------------*/
402/*---------------------------------------------------------------------------*/
411{
412 Int32 n = m_p->m_lazy_nb_source;
413 m_is_lazy = false;
414 IncrementalItemConnectivityContainer::m_lazy_pool.release(m_p->m_lazy_buffer);
415 m_p->m_connectivity_nb_item_array.resize(n);
416 m_p->m_connectivity_index_array.resize(n);
417 m_p->m_connectivity_nb_item_array.fill(0);
418 m_p->m_connectivity_index_array.fill(0);
419 _notifyConnectivityIndexChanged();
420 _notifyConnectivityNbItemChanged();
421}
422
423/*---------------------------------------------------------------------------*/
424/*---------------------------------------------------------------------------*/
425
426void IncrementalItemConnectivityBase::
427_notifyConnectivityIndexChanged()
428{
429 // While lazy the real array is empty on purpose: publish the zero views
430 // instead, so every caller of this method keeps working unchanged.
431 if (m_is_lazy) {
433 return;
434 }
435 m_connectivity_index = m_p->m_connectivity_index_array.view();
436 if (m_item_connectivity_list)
437 m_item_connectivity_list->_setConnectivityIndex(m_item_connectivity_index, m_connectivity_index);
438}
439
440/*---------------------------------------------------------------------------*/
441/*---------------------------------------------------------------------------*/
442
443void IncrementalItemConnectivityBase::
444_notifyConnectivityNbItemChanged()
445{
446 if (m_is_lazy) {
448 return;
449 }
450 m_connectivity_nb_item = m_p->m_connectivity_nb_item_array.view();
451 if (m_item_connectivity_list)
452 m_item_connectivity_list->_setConnectivityNbItem(m_item_connectivity_index, m_connectivity_nb_item);
453}
454
455/*---------------------------------------------------------------------------*/
456/*---------------------------------------------------------------------------*/
457
458void IncrementalItemConnectivityBase::
459_setMaxNbConnectedItemsInConnectivityList()
460{
461 if (m_item_connectivity_list)
462 m_item_connectivity_list->_setMaxNbConnectedItem(m_item_connectivity_index, m_p->m_max_nb_item);
463}
464
465/*---------------------------------------------------------------------------*/
466/*---------------------------------------------------------------------------*/
473{
474 // The variable was filled from outside (a restore): the connectivity is no
475 // longer empty, whatever it held before.
476 if (m_is_lazy && m_p->m_connectivity_nb_item_array.size() > 0) {
477 m_is_lazy = false;
478 IncrementalItemConnectivityContainer::m_lazy_pool.release(m_p->m_lazy_buffer);
479 m_p->m_lazy_nb_source = m_p->m_connectivity_nb_item_array.size();
480 _notifyConnectivityIndexChanged();
481 }
482 _notifyConnectivityNbItemChanged();
483 _computeMaxNbConnectedItem();
484}
485
486/*---------------------------------------------------------------------------*/
487/*---------------------------------------------------------------------------*/
488
489void IncrementalItemConnectivityBase::
490_setNewMaxNbConnectedItems(Int32 new_max)
491{
492 if (new_max > m_p->m_max_nb_item) {
493 m_p->m_max_nb_item = new_max;
494 _setMaxNbConnectedItemsInConnectivityList();
495 }
496}
497
498/*---------------------------------------------------------------------------*/
499/*---------------------------------------------------------------------------*/
500
501void IncrementalItemConnectivityBase::
502_computeMaxNbConnectedItem()
503{
504 // Force reset to ensure it is updated
505 m_p->m_max_nb_item = -1;
506 Int32 max_nb_item = 0;
507 for (Int32 x : m_connectivity_nb_item)
508 if (x > max_nb_item)
509 max_nb_item = x;
510 _setNewMaxNbConnectedItems(max_nb_item);
511}
512
513/*---------------------------------------------------------------------------*/
514/*---------------------------------------------------------------------------*/
515
517maxNbConnectedItem() const
518{
519 return m_p->m_max_nb_item;
520}
521
522/*---------------------------------------------------------------------------*/
523/*---------------------------------------------------------------------------*/
533{
534 info(4) << "setItemConnectivityList name=" << name() << " ilist=" << ilist << " index=" << index;
535 m_item_connectivity_list = ilist;
536 m_item_connectivity_index = index;
537 _notifyConnectivityListChanged();
538 _notifyConnectivityIndexChanged();
539 _notifyConnectivityNbItemChanged();
540 _setMaxNbConnectedItemsInConnectivityList();
541}
542
543/*---------------------------------------------------------------------------*/
544/*---------------------------------------------------------------------------*/
545
548{
549 if (m_is_lazy) {
550 // Same size as the compaction of the variables would have left.
551 m_p->m_lazy_nb_source = new_to_old_ids.size();
552 return;
553 }
554 if (m_p->isAllocated()) {
555 m_p->m_connectivity_nb_item_variable.variable()->compact(new_to_old_ids);
556 m_p->m_connectivity_index_variable.variable()->compact(new_to_old_ids);
557 _notifyConnectivityNbItemChanged();
558 _notifyConnectivityIndexChanged();
559 }
560}
561
562/*---------------------------------------------------------------------------*/
563/*---------------------------------------------------------------------------*/
564
567{
568 Int32ArrayView ids = m_connectivity_list;
569 const Integer n = ids.size();
570 for (Integer i = 0; i < n; ++i)
571 if (ids[i] != NULL_ITEM_LOCAL_ID)
572 ids[i] = old_to_new_ids[ids[i]];
573}
574
575/*---------------------------------------------------------------------------*/
576/*---------------------------------------------------------------------------*/
577
579_connectedItems(ItemLocalId item, ConnectivityItemVector& con_items) const
580{
581 return con_items.resizeAndCopy(_connectedItemsLocalId(item));
582}
583
584/*---------------------------------------------------------------------------*/
585/*---------------------------------------------------------------------------*/
586
587ItemConnectivityContainerView IncrementalItemConnectivityBase::
588connectivityContainerView() const
589{
590 return { m_connectivity_list, m_connectivity_index, m_connectivity_nb_item };
591}
592
593/*---------------------------------------------------------------------------*/
594/*---------------------------------------------------------------------------*/
595
596IndexedItemConnectivityViewBase IncrementalItemConnectivityBase::
597connectivityView() const
598{
599 return { connectivityContainerView(), _sourceFamily()->itemKind(), _targetFamily()->itemKind() };
600}
601
602/*---------------------------------------------------------------------------*/
603/*---------------------------------------------------------------------------*/
604
605IndexedItemConnectivityAccessor IncrementalItemConnectivityBase::
606connectivityAccessor() const
607{
608 return IndexedItemConnectivityAccessor(connectivityView(), _targetFamily());
609}
610
611/*---------------------------------------------------------------------------*/
612/*---------------------------------------------------------------------------*/
613
619
620/*---------------------------------------------------------------------------*/
621/*---------------------------------------------------------------------------*/
622
623void IncrementalItemConnectivityBase::
624dumpInfos()
625{
626 info() << "Infos index=" << m_connectivity_index;
627 info() << "Infos nb_item=" << m_connectivity_nb_item;
628 info() << "Infos list=" << m_connectivity_list;
629}
630
631/*---------------------------------------------------------------------------*/
632/*---------------------------------------------------------------------------*/
633
634/*---------------------------------------------------------------------------*/
635/*---------------------------------------------------------------------------*/
636
637IncrementalItemConnectivity::
638IncrementalItemConnectivity(IItemFamily* source_family, IItemFamily* target_family,
639 const String& aname)
640: IncrementalItemConnectivityBase(source_family, target_family, aname)
641, m_nb_add(0)
642, m_nb_remove(0)
643, m_nb_memcopy(0)
644, m_pre_allocated_size(0)
645{
646 m_pre_allocated_size = _sourceFamily()->properties()->getIntegerWithDefault(name() + "PreallocSize", 0);
647 info(4) << "PreallocSize1 var=" << m_p->m_var_name << " v=" << m_pre_allocated_size;
648
649 // ARCANE_LAZY_CONNECTIVITY=1 leaves the connectivity unallocated until it
650 // gets its first connected item.
651 auto is_lazy = Convert::Type<Int32>::tryParseFromEnvironment("ARCANE_LAZY_CONNECTIVITY", true);
652 m_is_lazy = is_lazy && is_lazy.value() != 0;
653
654 // Checks if the null entity needs to be added at the beginning of the list.
655 _checkAddNullItem();
656}
657
658/*---------------------------------------------------------------------------*/
659/*---------------------------------------------------------------------------*/
660
661IncrementalItemConnectivity::
662~IncrementalItemConnectivity()
663{
664 if (m_is_lazy)
666 info(4) << " connectivity name=" << name()
667 << " prealloc_size=" << m_pre_allocated_size
668 << " nb_add=" << m_nb_add
669 << " nb_remove=" << m_nb_remove
670 << " nb_memcopy=" << m_nb_memcopy;
671}
672
673/*---------------------------------------------------------------------------*/
674/*---------------------------------------------------------------------------*/
675
676inline Integer IncrementalItemConnectivity::
677_increaseConnectivityList(Int32 new_lid)
678{
679 Integer pos_in_list = m_connectivity_list.size();
680 m_p->m_connectivity_list_array.add(new_lid);
681 _notifyConnectivityListChanged();
682 return pos_in_list;
683}
684
685/*---------------------------------------------------------------------------*/
686/*---------------------------------------------------------------------------*/
687
688inline Integer IncrementalItemConnectivity::
689_increaseConnectivityList(Int32 new_lid, Integer nb_value)
690{
691 Integer pos_in_list = m_connectivity_list.size();
692 m_p->m_connectivity_list_array.addRange(new_lid, nb_value);
693 _notifyConnectivityListChanged();
694 return pos_in_list;
695}
696
697/*---------------------------------------------------------------------------*/
698/*---------------------------------------------------------------------------*/
699
700void IncrementalItemConnectivity::
701_resetConnectivityList()
702{
703 m_p->m_connectivity_list_array.clear();
704 _notifyConnectivityListChanged();
705 _checkAddNullItem();
706}
707
708/*---------------------------------------------------------------------------*/
709/*---------------------------------------------------------------------------*/
710
711void IncrementalItemConnectivity::
712_increaseIndexList(Int32 lid, Integer size, Int32 target_lid)
713{
714 Integer added_range = (m_pre_allocated_size > 0) ? m_pre_allocated_size : 1;
715 ++m_nb_memcopy;
716 Integer pos_in_index = m_connectivity_index[lid];
717 Integer new_pos_in_list = _increaseConnectivityList(NULL_ITEM_LOCAL_ID, size + added_range);
718 ArrayView<Int32> current_list(size, &(m_connectivity_list[pos_in_index]));
719 ArrayView<Int32> new_list(size + 1, &(m_connectivity_list[new_pos_in_list]));
720 new_list.copy(current_list);
721 // Adds the new entity to the end of the connectivity list
722 // TODO: look into sorting by increasing uid().
723 new_list[size] = target_lid;
724 m_connectivity_index[lid] = new_pos_in_list;
725}
726
727/*---------------------------------------------------------------------------*/
728/*---------------------------------------------------------------------------*/
729
731addConnectedItem(ItemLocalId source_item, ItemLocalId target_item)
732{
734 ++m_nb_add;
735 const Int32 lid = source_item.localId();
736 const Int32 target_lid = target_item.localId();
737 Integer size = m_connectivity_nb_item[lid];
738 // Adds a connected item.
739 // For now, the functionality is basic.
740 // The items are always added to the end of m_p->m_connectivity_list.
741 // If there are none, it is enough to add to the end.
742 // If there are already some, it is necessary to allocate at the end of
743 // m_p->m_connectivity_list enough \a size+1 elements and
744 // we copy the previous connectivity to the new location.
745 // Naturally, over time the list will always grow
746 // because the gaps are not reused.
747 if (m_pre_allocated_size != 0) {
748 // In case of preallocation, we allocate in blocks of size 'm_pre_allocated_size'.
749 // We must therefore reallocate if the size is a multiple of m_pre_allocated_size
750 if (size == 0) {
751 Integer new_pos_in_list = _increaseConnectivityList(NULL_ITEM_LOCAL_ID, m_pre_allocated_size);
752 m_connectivity_index[lid] = new_pos_in_list;
753 m_connectivity_list[new_pos_in_list] = target_lid;
754 }
755 else {
756 if (size < m_pre_allocated_size || (size % m_pre_allocated_size) != 0) {
757 Integer index = m_connectivity_index[lid];
758 m_connectivity_list[index + size] = target_lid;
759 }
760 else {
761 _increaseIndexList(lid, size, target_lid);
762 }
763 }
764 }
765 else {
766 if (size == 0) {
767 Integer new_pos_in_list = _increaseConnectivityList(target_lid);
768 m_connectivity_index[lid] = new_pos_in_list;
769 }
770 else {
771 _increaseIndexList(lid, size, target_lid);
772 }
773 }
774 ++(m_connectivity_nb_item[lid]);
775 _setNewMaxNbConnectedItems(m_connectivity_nb_item[lid]);
776}
777
778/*---------------------------------------------------------------------------*/
779/*---------------------------------------------------------------------------*/
780
781Integer IncrementalItemConnectivity::
782_computeAllocSize(Integer nb_item)
783{
784 if (m_pre_allocated_size != 0) {
785 // Allocates a multiple of \a m_pre_allocated_size
786 Integer alloc_size = nb_item / m_pre_allocated_size;
787 if (alloc_size == 0)
788 return m_pre_allocated_size;
789 if ((nb_item % m_pre_allocated_size) == 0)
790 return nb_item;
791 return m_pre_allocated_size * (alloc_size + 1);
792 }
793 return nb_item;
794}
795
796/*---------------------------------------------------------------------------*/
797/*---------------------------------------------------------------------------*/
798
799void IncrementalItemConnectivity::
800addConnectedItems(ItemLocalId source_item, Integer nb_item)
801{
803 const Int32 lid = source_item.localId();
804 Integer size = m_connectivity_nb_item[lid];
805 if (size != 0)
806 ARCANE_FATAL("source_item already have connected items");
807 Integer alloc_size = _computeAllocSize(nb_item);
808 Integer new_pos_in_list = _increaseConnectivityList(NULL_ITEM_LOCAL_ID, alloc_size);
809 m_connectivity_index[lid] = new_pos_in_list;
810 m_connectivity_nb_item[lid] += nb_item;
811 _setNewMaxNbConnectedItems(m_connectivity_nb_item[lid]);
812}
813
814/*---------------------------------------------------------------------------*/
815/*---------------------------------------------------------------------------*/
816
818setConnectedItems(ItemLocalId source_item, Int32ConstArrayView target_local_ids)
819{
821 removeConnectedItems(source_item);
822 addConnectedItems(source_item, target_local_ids.size());
823 replaceConnectedItems(source_item, target_local_ids);
824}
825
826/*---------------------------------------------------------------------------*/
827/*---------------------------------------------------------------------------*/
828
832{
834 const Int32 nb_source = nb_items.size();
835 if (indexes.size() != nb_source)
836 ARCANE_FATAL("Incoherent sizes nb_items={0} indexes={1}", nb_source, indexes.size());
837 m_p->m_connectivity_nb_item_array.resize(nb_source);
838 m_p->m_connectivity_index_array.resize(nb_source);
839 m_p->m_connectivity_list_array.resize(list.size());
840 _notifyConnectivityNbItemChanged();
841 _notifyConnectivityIndexChanged();
842 _notifyConnectivityListChanged();
843 m_connectivity_nb_item.copy(nb_items);
844 m_connectivity_index.copy(indexes);
845 m_connectivity_list.copy(list);
846 m_p->m_max_nb_item = 0;
847 _computeMaxNbConnectedItem();
848}
849
850/*---------------------------------------------------------------------------*/
851/*---------------------------------------------------------------------------*/
852
854resizeBulkConnectivity(Int32 nb_source, Int64 list_size, Int32ArrayView& nb_items,
855 Int32ArrayView& indexes, Int32ArrayView& list)
856{
858 m_p->m_connectivity_nb_item_array.resize(nb_source);
859 m_p->m_connectivity_index_array.resize(nb_source);
860 m_p->m_connectivity_list_array.resize(list_size);
861 _notifyConnectivityNbItemChanged();
862 _notifyConnectivityIndexChanged();
863 _notifyConnectivityListChanged();
864 nb_items = m_connectivity_nb_item;
865 indexes = m_connectivity_index;
866 list = m_connectivity_list;
867}
868
869/*---------------------------------------------------------------------------*/
870/*---------------------------------------------------------------------------*/
871
874{
875 m_p->m_max_nb_item = 0;
876 _computeMaxNbConnectedItem();
877}
878
879/*---------------------------------------------------------------------------*/
880/*---------------------------------------------------------------------------*/
881
884{
886 Int32 lid = source_item.localId();
887 m_connectivity_nb_item[lid] = 0;
888}
889
890/*---------------------------------------------------------------------------*/
891/*---------------------------------------------------------------------------*/
892
894removeConnectedItem(ItemLocalId source_item, ItemLocalId target_item)
895{
897 ++m_nb_remove;
898 Int32 lid = source_item.localId();
899 Int32 target_lid = target_item.localId();
900 Integer size = m_connectivity_nb_item[lid];
901 Int32* items = &(m_connectivity_list[m_connectivity_index[lid]]);
902 mesh_utils::removeItemAndKeepOrder(Int32ArrayView(size, items), target_lid);
903 --(m_connectivity_nb_item[lid]);
904}
905
906/*---------------------------------------------------------------------------*/
907/*---------------------------------------------------------------------------*/
908
910replaceConnectedItem(ItemLocalId source_item, Integer index, ItemLocalId target_item)
911{
913 Int32 lid = source_item.localId();
914 Int32 target_lid = target_item.localId();
915 ARCANE_CHECK_AT(index, m_connectivity_nb_item[lid]);
916 m_connectivity_list[m_connectivity_index[lid] + index] = target_lid;
917}
918
919/*---------------------------------------------------------------------------*/
920/*---------------------------------------------------------------------------*/
921
923replaceConnectedItems(ItemLocalId source_item, Int32ConstArrayView target_local_ids)
924{
926 Int32 lid = source_item.localId();
927 Int32 n = target_local_ids.size();
928 if (n > 0) {
929 ARCANE_CHECK_AT(n - 1, m_connectivity_nb_item[lid]);
930 const Int32 pos = m_connectivity_index[lid];
931 for (Integer i = 0; i < n; ++i)
932 m_connectivity_list[pos + i] = target_local_ids[i];
933 }
934}
935
936/*---------------------------------------------------------------------------*/
937/*---------------------------------------------------------------------------*/
938
940hasConnectedItem(ItemLocalId source_item, ItemLocalId target_local_id) const
941{
942 bool has_connection = false;
943 auto connected_items = _connectedItemsLocalId(source_item);
944 if (std::find(connected_items.begin(), connected_items.end(), target_local_id) != connected_items.end())
945 has_connection = true;
946 return has_connection;
947}
948
949/*---------------------------------------------------------------------------*/
950/*---------------------------------------------------------------------------*/
951
954{
955 Int32 lid = item.localId();
956 if (m_is_lazy) {
957 _lazyNotifySourceItemAdded(lid);
958 return;
959 }
960 m_p->_checkResize(lid);
961 _notifyConnectivityIndexChanged();
962 _notifyConnectivityNbItemChanged();
963
964 m_connectivity_nb_item[lid] = 0;
965 m_connectivity_index[lid] = 0;
966}
967
968/*---------------------------------------------------------------------------*/
969/*---------------------------------------------------------------------------*/
970
971void IncrementalItemConnectivity::
972_internalNotifySourceItemsAdded(ConstArrayView<Int32> local_ids)
973{
974 // Pre-calculates the maximum of the local_ids for resizing.
975 Int32 nb_item = local_ids.size();
976 if (nb_item <= 0)
977 return;
978 Int32 max_lid = local_ids[0];
979 for (Int32 lid : local_ids)
980 max_lid = math::max(max_lid, lid);
981
982 if (m_is_lazy) {
983 // Nothing to write: the zero views already read 0 for every source item.
984 _lazyNotifySourceItemAdded(max_lid);
985 return;
986 }
987 m_p->_checkResize(max_lid);
988 _notifyConnectivityIndexChanged();
989 _notifyConnectivityNbItemChanged();
990
991 for (Int32 lid : local_ids) {
992 m_connectivity_nb_item[lid] = 0;
993 m_connectivity_index[lid] = 0;
994 }
995}
996
997/*---------------------------------------------------------------------------*/
998/*---------------------------------------------------------------------------*/
999
1002{
1003 if (m_is_lazy) {
1004 // Saved empty, and the restore re-allocates the items without notifying
1005 // the connectivities one by one: cover every local id now, or the first
1006 // nbConnectedItem() reads past the end of a zero buffer of length 0.
1007 Int32 max_local_id = _sourceFamily()->maxLocalId();
1008 if (max_local_id > 0)
1009 _lazyNotifySourceItemAdded(max_local_id - 1);
1010 }
1011 m_pre_allocated_size = _sourceFamily()->properties()->getIntegerWithDefault(name() + "PreallocSize", 0);
1012 info(4) << "PreallocSize2 var=" << m_p->m_var_name << " v=" << m_pre_allocated_size;
1013
1014 // There is practically nothing to do for the variables because the views are correctly updated via the observables on the variables.
1015}
1016
1017/*---------------------------------------------------------------------------*/
1018/*---------------------------------------------------------------------------*/
1019
1021setPreAllocatedSize(Integer prealloc_size)
1022{
1023 // No need to leave the lazy state: this writes m_pre_allocated_size and the
1024 // connectivity LIST, never a per-source array.
1025 if (m_pre_allocated_size < 0)
1026 throw ArgumentException(A_FUNCINFO,
1027 String::format("Invalid prealloc_size v={0}",
1028 prealloc_size));
1029
1030 // Does nothing if we have already allocated entities, otherwise it would make
1031 // the allocations inconsistent.
1032 // NOTE: we could allow it, but that would require rebuilding
1033 // the connectivity indices. A call to compactConnectivityList()
1034 // would suffice.
1035 Integer nb_source = m_is_lazy ? m_p->m_lazy_nb_source : m_connectivity_nb_item.size();
1036 if (nb_source != 0)
1037 return;
1038
1039 m_pre_allocated_size = prealloc_size;
1040 _sourceFamily()->properties()->setInteger(name() + "PreallocSize", prealloc_size);
1041
1042 // Even if there are no entities, m_p->m_connectivity_list_array is not
1043 // empty because we called _checkkAddNulItem() in the constructor. We must
1044 // now reallocate it with the new pre-allocation value.
1045 _resetConnectivityList();
1046}
1047
1048/*---------------------------------------------------------------------------*/
1049/*---------------------------------------------------------------------------*/
1050
1052dumpStats(std::ostream& out) const
1053{
1054 Int64 mem1 = m_p->m_connectivity_list_array.capacity();
1055 Int64 mem2 = m_p->m_connectivity_index_array.capacity();
1056 Int64 mem3 = m_p->m_connectivity_nb_item_array.capacity();
1057 Int64 allocated_size = mem1 + mem2 + mem3;
1058 allocated_size *= sizeof(Int32);
1059
1060 out << " connectiviy name=" << name()
1061 << " prealloc_size=" << m_pre_allocated_size
1062 << " nb_add=" << m_nb_add
1063 << " nb_remove=" << m_nb_remove
1064 << " nb_memcopy=" << m_nb_memcopy
1065 << " list_size=" << m_connectivity_list.size()
1066 << " list_capacity=" << mem1
1067 << " index_size=" << m_connectivity_index.size()
1068 << " index_capacity=" << mem2
1069 << " nb_item_size=" << m_connectivity_nb_item.size()
1070 << " nb_item_capacity=" << mem3
1071 << " allocated_size=" << allocated_size;
1072}
1073
1074/*---------------------------------------------------------------------------*/
1075/*---------------------------------------------------------------------------*/
1076
1077void IncrementalItemConnectivityBase::
1078_shrinkMemory()
1079{
1080 m_p->m_connectivity_list_array.shrink();
1081 m_p->m_connectivity_index_array.shrink();
1082 m_p->m_connectivity_nb_item_array.shrink();
1083 _notifyConnectivityIndexChanged();
1084 _notifyConnectivityNbItemChanged();
1085 _notifyConnectivityListChanged();
1086}
1087
1088/*---------------------------------------------------------------------------*/
1089/*---------------------------------------------------------------------------*/
1090
1091void IncrementalItemConnectivityBase::
1092_addMemoryInfos(ItemConnectivityMemoryInfo& mem_info)
1093{
1094 Int64 s1 = m_p->m_connectivity_list_array.size();
1095 Int64 s2 = m_p->m_connectivity_index_array.size();
1096 Int64 s3 = m_p->m_connectivity_nb_item_array.size();
1097 mem_info.m_total_size += s1 + s2 + s3;
1098
1099 Int64 c1 = m_p->m_connectivity_list_array.capacity();
1100 Int64 c2 = m_p->m_connectivity_index_array.capacity();
1101 Int64 c3 = m_p->m_connectivity_nb_item_array.capacity();
1102 mem_info.m_total_capacity += c1 + c2 + c3;
1103}
1104
1105/*---------------------------------------------------------------------------*/
1106/*---------------------------------------------------------------------------*/
1107
1108void IncrementalItemConnectivity::
1109_checkAddNullItem()
1110{
1111 // If the connectivity list is empty, create an element
1112 // (or several if m_pre_allocated_size>0) to contain the null entity.
1113 // This allows retrieving the list of connectivities for an entity even if
1114 // it is empty.
1115 if (m_connectivity_list.size() == 0) {
1116 if (m_pre_allocated_size > 0) {
1117 _increaseConnectivityList(NULL_ITEM_LOCAL_ID, m_pre_allocated_size);
1118 }
1119 else {
1120 _increaseConnectivityList(NULL_ITEM_LOCAL_ID);
1121 }
1122 }
1123}
1124
1125/*---------------------------------------------------------------------------*/
1126/*---------------------------------------------------------------------------*/
1139{
1140 if (m_is_lazy)
1141 return; // every nb_item is 0, the index is 0 everywhere, the list is the null item
1142 info(4) << "Begin Compacting IncrementalItemConnectivity name=" << name()
1143 << " new_size=" << m_connectivity_list.size()
1144 << " prealloc_size=" << m_pre_allocated_size;
1145 // TODO: try to find a way to only compact if
1146 // it is necessary. One way would be to count the number of calls to
1147 // _increaseIndexList() since the last compaction.
1148 UniqueArray<Int32> old_connectivity_list(m_connectivity_list);
1149 Integer old_size = old_connectivity_list.size();
1150 Integer nb_item = m_connectivity_nb_item.size();
1151 m_p->m_connectivity_list_array.clear();
1152 _notifyConnectivityListChanged();
1153 _checkAddNullItem();
1154 Integer new_pos_in_list = m_p->m_connectivity_list_array.size();
1155 Int32 pre_allocated_size = m_pre_allocated_size;
1156 for (Integer i = 0; i < nb_item; ++i) {
1157 Int32 lid = i;
1158 Int32 nb = m_connectivity_nb_item[lid];
1159 if (nb == 0) {
1160 m_connectivity_index[lid] = 0;
1161 continue;
1162 }
1163 Int32 index = m_connectivity_index[lid];
1164 Int32ConstArrayView con_list(nb, old_connectivity_list.data() + index);
1165 Integer alloc_size = _computeAllocSize(nb);
1166 m_connectivity_index[lid] = new_pos_in_list;
1167 new_pos_in_list += alloc_size;
1168 //info() << "NEW_POS_IN_LIST=" << new_pos_in_list << " nb=" << nb << " alloc_size=" << alloc_size;
1169 // Checks that the position is indeed a multiple of pre_allocated_size.
1170 if (pre_allocated_size != 0) {
1171 Int32 pos_modulo = new_pos_in_list % pre_allocated_size;
1172 if (pos_modulo != 0)
1173 ARCANE_FATAL("Bad position i={0} pos={1} pre_alloc_size={2} modulo={3}",
1174 i, new_pos_in_list, pre_allocated_size, pos_modulo);
1175 }
1176 m_p->m_connectivity_list_array.addRange(con_list);
1177 // If pre-allocation, fill the remaining elements with the null entity..
1178 if (alloc_size != nb)
1179 m_p->m_connectivity_list_array.addRange(NULL_ITEM_LOCAL_ID, alloc_size - nb);
1180 if (m_pre_allocated_size == 0 && nb == 0)
1181 m_connectivity_index[lid] = 0;
1182 }
1183 _notifyConnectivityListChanged();
1184 _computeMaxNbConnectedItem();
1185 info(4) << "Compacting IncrementalItemConnectivity name=" << name()
1186 << " nb_item=" << nb_item << " old_size=" << old_size
1187 << " new_size=" << m_connectivity_list.size()
1188 << " prealloc_size=" << m_pre_allocated_size;
1189}
1190
1191/*---------------------------------------------------------------------------*/
1192/*---------------------------------------------------------------------------*/
1193
1194/*---------------------------------------------------------------------------*/
1195/*---------------------------------------------------------------------------*/
1196
1197/*---------------------------------------------------------------------------*/
1198/*---------------------------------------------------------------------------*/
1199
1200OneItemIncrementalItemConnectivity::
1201OneItemIncrementalItemConnectivity(IItemFamily* source_family, IItemFamily* target_family,
1202 const String& aname)
1203: IncrementalItemConnectivityBase(source_family, target_family, aname)
1204{
1205 info(4) << "Using fixed OneItem connectivity for name=" << name();
1206}
1207
1208/*---------------------------------------------------------------------------*/
1209/*---------------------------------------------------------------------------*/
1210
1211OneItemIncrementalItemConnectivity::
1212~OneItemIncrementalItemConnectivity()
1213{
1214}
1215
1216/*---------------------------------------------------------------------------*/
1217/*---------------------------------------------------------------------------*/
1218
1220addConnectedItem(ItemLocalId source_item, ItemLocalId target_item)
1221{
1222 Int32 lid = source_item.localId();
1223 Integer size = m_connectivity_nb_item[lid];
1224 if (size != 0)
1225 ARCANE_FATAL("source_item already have connected items");
1226 Int32 target_lid = target_item.localId();
1227 m_connectivity_list[lid] = target_lid;
1228 m_connectivity_nb_item[lid] = 1;
1229 _setNewMaxNbConnectedItems(1);
1230}
1231
1232/*---------------------------------------------------------------------------*/
1233/*---------------------------------------------------------------------------*/
1234
1237{
1238 Int32 lid = source_item.localId();
1239 m_connectivity_nb_item[lid] = 0;
1240}
1241
1242/*---------------------------------------------------------------------------*/
1243/*---------------------------------------------------------------------------*/
1244
1246removeConnectedItem(ItemLocalId source_item, ItemLocalId target_item)
1247{
1248 Int32 lid = source_item.localId();
1249 Int32 target_local_id = target_item.localId();
1250 Integer size = m_connectivity_nb_item[lid];
1251 if (size != 1)
1252 ARCANE_FATAL("source_item has no connected item");
1253 Int32 target_lid = m_connectivity_list[lid];
1254 if (target_lid != target_local_id)
1255 ARCANE_FATAL("source_item is not connected to item with wanted_lid={0} current_lid={1}",
1256 target_local_id, target_lid);
1257 m_connectivity_nb_item[lid] = 0;
1258 m_connectivity_list[lid] = NULL_ITEM_LOCAL_ID;
1259}
1260
1261/*---------------------------------------------------------------------------*/
1262/*---------------------------------------------------------------------------*/
1263
1265replaceConnectedItem(ItemLocalId source_item, Integer index, ItemLocalId target_item)
1266{
1267 if (index != 0)
1268 ARCANE_FATAL("index has to be '0'");
1269 Int32 lid = source_item.localId();
1270 Int32 target_lid = target_item.localId();
1271 m_connectivity_list[lid] = target_lid;
1272}
1273
1274/*---------------------------------------------------------------------------*/
1275/*---------------------------------------------------------------------------*/
1276
1278replaceConnectedItems(ItemLocalId source_item, Int32ConstArrayView target_local_ids)
1279{
1280 Int32 lid = source_item.localId();
1281 Integer n = target_local_ids.size();
1282 if (n == 0)
1283 return;
1284 if (n != 1)
1285 ARCANE_FATAL("Invalid size for target_list. value={0} (expected 1)", n);
1286 m_connectivity_list[lid] = target_local_ids[0];
1287}
1288
1289/*---------------------------------------------------------------------------*/
1290/*---------------------------------------------------------------------------*/
1291
1293hasConnectedItem(ItemLocalId source_item,
1294 ItemLocalId target_local_id) const
1295{
1296 if (m_connectivity_list[source_item.localId()] == target_local_id.localId())
1297 return true;
1298 else
1299 return false;
1300}
1301
1302/*---------------------------------------------------------------------------*/
1303/*---------------------------------------------------------------------------*/
1304
1305void OneItemIncrementalItemConnectivity::
1306_checkResizeConnectivityList()
1307{
1308 // Resizes the connectivity list with the same number of elements
1309 // as the number of entities.
1310 Integer wanted_size = m_connectivity_nb_item.size();
1311 Integer list_size = m_connectivity_list.size();
1312 if (list_size == wanted_size)
1313 return;
1314 Integer capacity = m_p->m_connectivity_list_array.capacity();
1315 if (wanted_size >= capacity) {
1316 m_p->m_connectivity_list_array.reserve(m_p->m_connectivity_nb_item_array.capacity());
1317 }
1318 m_p->m_connectivity_list_array.resize(wanted_size);
1319 _notifyConnectivityListChanged();
1320}
1321
1322/*---------------------------------------------------------------------------*/
1323/*---------------------------------------------------------------------------*/
1324
1327{
1328 Int32 lid = item.localId();
1329 m_p->_checkResize(lid);
1330 _notifyConnectivityIndexChanged();
1331 _notifyConnectivityNbItemChanged();
1332 _checkResizeConnectivityList();
1333
1334 m_connectivity_nb_item[lid] = 0;
1335 m_connectivity_index[lid] = lid;
1336 m_connectivity_list[lid] = NULL_ITEM_LOCAL_ID;
1337}
1338
1339/*---------------------------------------------------------------------------*/
1340/*---------------------------------------------------------------------------*/
1341
1344{
1345 if (m_is_lazy) {
1346 // Same size as the compaction of the variables would have left.
1347 m_p->m_lazy_nb_source = new_to_old_ids.size();
1348 return;
1349 }
1350 // For this implementation, the indices should not be updated
1351 // because otherwise we won't have m_connectivity_index[lid] = lid.
1352 // TODO: since m_connectivity_nb_item is originally 1 everywhere, it's
1353 // not useful to do it on this variable either, but
1354 // since there might be entities for which nb_item is 0 if
1355 // no connected entity was added, it is better to perform the compaction.
1356
1357 m_p->m_connectivity_nb_item_variable.variable()->compact(new_to_old_ids);
1358 _notifyConnectivityNbItemChanged();
1359
1360 // Since with this implementation the connectivity list is indexed
1361 // by the localId() of the source entity, it must be compacted
1362 // m_p->m_connectivity_list_variable.
1363 m_p->m_connectivity_list_variable.variable()->compact(new_to_old_ids);
1364 _notifyConnectivityListChanged();
1365
1366 // Does not compact the indices but still updates the size
1367 // of the array.
1368 m_p->m_connectivity_index_array.resize(m_connectivity_nb_item.size());
1369 _notifyConnectivityIndexChanged();
1370}
1371
1372/*---------------------------------------------------------------------------*/
1373/*---------------------------------------------------------------------------*/
1374
1379
1380/*---------------------------------------------------------------------------*/
1381/*---------------------------------------------------------------------------*/
1382
1384dumpStats(std::ostream& out) const
1385{
1386 size_t allocated_size = m_p->m_connectivity_list_array.capacity() + m_p->m_connectivity_index_array.capacity() + m_p->m_connectivity_nb_item_array.capacity();
1387 allocated_size *= sizeof(Int32);
1388
1389 out << " connectiviy name=" << name()
1390 << " list_size=" << m_connectivity_list.size()
1391 << " index_size=" << m_connectivity_index.size()
1392 << " nb_item_size=" << m_connectivity_nb_item.size()
1393 << " allocated_size=" << allocated_size;
1394}
1395
1396/*---------------------------------------------------------------------------*/
1397/*---------------------------------------------------------------------------*/
1398
1399void OneItemIncrementalItemConnectivity::
1400compactConnectivityList()
1401{
1402 _computeMaxNbConnectedItem();
1403}
1404
1405/*---------------------------------------------------------------------------*/
1406/*---------------------------------------------------------------------------*/
1407
1408} // End namespace Arcane::mesh
1409
1410/*---------------------------------------------------------------------------*/
1411/*---------------------------------------------------------------------------*/
#define ARCANE_FATAL(...)
Macro throwing a FatalErrorException.
Utility functions for the mesh.
void removeItemAndKeepOrder(Int32ArrayView items, Int32 local_id)
Removes an entity while preserving order.
Integer capacity() const
Capacity (number of allocated elements) of the vector.
Integer size() const
Number of elements in the vector.
constexpr Integer size() const noexcept
Returns the size of the array.
void shrink()
Reallocates to free unused memory.
void resize(Int64 s)
Changes the number of elements in the array to s.
const T * data() const
Access to the root of the array without any protection.
void reserve(Int64 new_capacity)
Reserves memory for new_capacity elements.
ArrayView< T > view() const
Mutable view of this array.
ItemVectorView resizeAndCopy(Int32ConstArrayView ids)
Positions the connectivity list with the entities specified by ids.
Constant view of an array of type T.
constexpr const_pointer data() const noexcept
Pointer to the allocated memory.
constexpr Integer size() const noexcept
Number of elements in the array.
Template class for converting a type.
Internal Arcane API for IIncrementalItemConnectivity.
virtual Integer preAllocatedSize() const =0
Number of entities pre-allocated for the connectivity of each entity.
Interface of an entity family.
Definition IItemFamily.h:85
virtual String name() const =0
Family name.
virtual eItemKind itemKind() const =0
Entity kind.
virtual IMesh * mesh() const =0
Associated mesh.
virtual Properties * properties()=0
Properties associated with this family.
@ PPrivate
Indicates that the variable is private.
Definition IVariable.h:103
Views of containers holding connectivity. This class allows the containers used to be opaque outside ...
Memory usage information for connectivities.
Int64 m_total_capacity
Total number of Int32 allocated (corresponds to the sum of capacity()).
Int64 m_total_size
Total number of Int32 used (corresponds to the sum of size()).
Connectivity information, for an entity family, allowing transition between old and new connectivity ...
void _setConnectivityNbItem(Int32 item_kind, ConstArrayView< Int32 > v)
Positions the array containing the number of connected entities.
void _setConnectivityList(Int32 item_kind, ArrayView< Int32 > v)
Positions the array containing the connectivity list.
void _setConnectivityIndex(Int32 item_kind, ConstArrayView< Int32 > v)
Positions the connectivity index array.
Index of an Item in a variable.
Definition ItemLocalId.h:42
View on a vector of entities.
List of observers.
Integer getIntegerWithDefault(const String &name, Integer default_value) const
Value of the property named name.
Reference to an instance.
Unicode character string constructor.
TraceMessage info() const
Flow for an information message.
1D data vector with value semantics (STL style).
Parameters necessary for building a variable.
Abstract class for managing connectivities.
String name() const final
Name of the connectivity.
void notifyEndUpdateFromMesh() override
Notifies that the mesh has just been updated.
void addMemoryInfos(ItemConnectivityMemoryInfo &mem_info) override
Adds the instance's memory information to mem_info.
void shrinkMemory() override
Minimally reduces memory usage for connectivities.
Base class for incremental item->item[] connectivities.
bool m_is_lazy
True while this connectivity has never had a connected item.
void _checkMaterialize()
Leaves the lazy state if this connectivity is still in it.
void notifySourceFamilyLocalIdChanged(Int32ConstArrayView new_to_old_ids) override
Notifies the connectivity that the source family has been compacted.
Int32 maxNbConnectedItem() const override
Maximum number of entities connected to a source entity.
void setItemConnectivityList(ItemInternalConnectivityList *ilist, Int32 index)
Indicates that this connectivity is associated with one of the connectivities of ItemInternal.
void reserveMemoryForNbSourceItems(Int32 n, bool pre_alloc_connectivity) override
Reserves memory for n source entities.
ItemVectorView _connectedItems(ItemLocalId item, ConnectivityItemVector &con_items) const final
Fills con_items with the entities connected to item.
void _publishLazyViews(Int32 nb_source)
Points both per-source views at the shared zero buffer, so a reader of nbConnectedItem() gets 0 for e...
IIncrementalItemConnectivityInternal * _internalApi() override
Internal Arcane API.
void _trimLazyViews()
Moves the lazy views to one zero buffer of the size of the mesh.
void _materialize()
Leaves the lazy state: allocates the two per-source arrays for real.
void notifyTargetFamilyLocalIdChanged(Int32ConstArrayView old_to_new_ids) override
Notifies the connectivity that the target family has been compacted.
Int32 m_lazy_nb_source
Lazy state: this connectivity has never had a connected item.
static LazyMemoryPool m_lazy_pool
Zero buffers read by the lazy views.
LazyMemoryPool::Buffer * m_lazy_buffer
Buffer of m_lazy_pool the lazy views point into.
void resizeBulkConnectivity(Int32 nb_source, Int64 list_size, Int32ArrayView &nb_items, Int32ArrayView &indexes, Int32ArrayView &list)
Sizes the storage for a bulk fill and hands out the arrays to write.
bool hasConnectedItem(ItemLocalId source_item, ItemLocalId target_local_id) const override
Tests the existence of a connectivity between source_item and the entity with localId() target_local_...
void setConnectedItems(ItemLocalId source_item, Int32ConstArrayView target_local_ids) override
Allocates and positions entities connected to source_item.
void compactConnectivityList()
Compresses the connectivity list.
void removeConnectedItem(ItemLocalId source_item, ItemLocalId target_local_id) override
Removes the entity with localId() target_local_id from the connectivity of source_item.
void endBulkConnectivity()
Closes a fill started by resizeBulkConnectivity().
void notifySourceItemAdded(ItemLocalId item) override
Notifies the connectivity that an entity has been added to the source family.
void addConnectedItem(ItemLocalId source_item, ItemLocalId target_local_id) override
Adds the entity with localId() target_local_id to the connectivity of source_item.
void removeConnectedItems(ItemLocalId source_item) override
Removes all entities connected to source_item.
void notifyReadFromDump() override
Notifies the connectivity that a read has been performed from a dump.
void setBulkConnectivity(Int32ConstArrayView nb_items, Int32ConstArrayView indexes, Int32ConstArrayView list)
Replaces the whole connectivity with one the caller already knows.
void dumpStats(std::ostream &out) const override
Dumps statistics on usage and memory used to the stream out.
void replaceConnectedItems(ItemLocalId source_item, Int32ConstArrayView target_local_ids) override
Replaces the entities of source_item with the entities with localId() target_local_ids.
void replaceConnectedItem(ItemLocalId source_item, Integer index, ItemLocalId target_local_id) override
Replaces the entity at index index of source_item with the entity with localId() target_local_id.
void setPreAllocatedSize(Integer value) final
Sets the number of entities to pre-allocate for the connectivity of each entity.
Zeros backing every lazy connectivity view of the process.
void release(Buffer *&buffer)
Stops reading buffer, and frees it if nothing else reads it.
void removeConnectedItem(ItemLocalId source_item, ItemLocalId target_local_id) override
Removes the entity with localId() target_local_id from the connectivity of source_item.
void replaceConnectedItems(ItemLocalId source_item, Int32ConstArrayView target_local_ids) override
Replaces the entities of source_item with the entities with localId() target_local_ids.
void addConnectedItem(ItemLocalId source_item, ItemLocalId target_local_id) override
Adds the entity with localId() target_local_id to the connectivity of source_item.
void notifyReadFromDump() override
Notifies the connectivity that a read has been performed from a dump.
bool hasConnectedItem(ItemLocalId source_item, ItemLocalId target_local_id) const override
Tests the existence of a connectivity between source_item and the entity with localId() target_local_...
void notifySourceFamilyLocalIdChanged(Int32ConstArrayView new_to_old_ids) override
Notifies the connectivity that the source family has been compacted.
void replaceConnectedItem(ItemLocalId source_item, Integer index, ItemLocalId target_local_id) override
Replaces the entity at index index of source_item with the entity with localId() target_local_id.
void notifySourceItemAdded(ItemLocalId item) override
Notifies the connectivity that an entity has been added to the source family.
void removeConnectedItems(ItemLocalId source_item) override
Removes all entities connected to source_item.
void dumpStats(std::ostream &out) const override
Dumps statistics on usage and memory used to the stream out.
T max(const T &a, const T &b, const T &c)
Returns the maximum of three elements.
Definition MathUtils.h:407
VariableRefArrayT< Int32 > VariableArrayInt32
Array variable of 32-bit integer type.
std::int64_t Int64
Signed integer type of 64 bits.
Int32 Integer
Type representing an integer.
ConstArrayView< Int32 > Int32ConstArrayView
C equivalent of a 1D array of 32-bit integers.
Definition UtilsTypes.h:476
ArrayView< Int32 > Int32ArrayView
C equivalent of a 1D array of 32-bit integers.
Definition UtilsTypes.h:447
std::int32_t Int32
Signed integer type of 32 bits.
auto makeRef(InstanceType *t) -> Ref< InstanceType >
Creates a reference on a pointer.
One zero buffer and the number of connectivities reading it.