wzarray.cxx
来自「有限元学习研究用源代码(老外的),供科研人员参考」· CXX 代码 · 共 229 行
CXX
229 行
#include "wzarray.hxx"
#include <stdlib.h>
//#include <iostream.h>
#define wzArrayTraceAllocation
#undef wzArrayTraceAllocation
wzIndex wzArrayStaticInitializationManager::count;
wzIndex wzArrayStaticInitializationManager::AllocationCount;
class wzAllocationStrategy{
public:
wzIndex MinimalAdditionalSize;
wzIndex MinimalSize;
wzFloat MinimalFactor;
wzIndex Multiple;
wzIndex suggested(wzIndex min, wzIndex old);
wzAllocationStrategy(wzFloat f=0,wzIndex m=0,wzIndex a=0,wzIndex s=0)
:MinimalAdditionalSize(a),MinimalSize(s),MinimalFactor(f),Multiple(m){;}
~wzAllocationStrategy();
};
static wzAllocationStrategy DefaultStrategy(1.2,0x10,100,0xf);
wzArrayStaticInitializationManager::wzArrayStaticInitializationManager()
{if(count++ == 0){
DefaultStrategy.MinimalFactor = 1.2;
DefaultStrategy.MinimalAdditionalSize = 100;
DefaultStrategy.MinimalSize = 0xf;
DefaultStrategy.Multiple = 0x10;
}}
wzArrayStaticInitializationManager::~wzArrayStaticInitializationManager()
{if(--count == 0){
if(AllocationCount!=0) wzMessage("unpaired allocation\n");
}}
wzArrayBody::wzArrayBody(wzMultipleArrayController& c, wzIndex s, wzIndex m)
:Base(0),Max(0),Shift(s),Index(0),From(0)
{reinitialize(c,s,m);}
void wzArrayBody::reinitialize(wzMultipleArrayController& c, wzIndex s, wzIndex m)
{reinitialize(); Shift=s; c.defineArray(this); if(m) c.Allocate(m);}
wzArrayBody::wzArrayBody(const wzMultipleArrayController& c,
wzIndex s, wzIndex m)
:Base(0),Max(0),Shift(s),Index(0),From(0)
{reinitialize(c,s,m);}
void wzArrayBody::reinitialize(const wzMultipleArrayController& c,
wzIndex s, wzIndex m)
{reinitialize(); Shift=s; Allocate(c.Max); if(m) Allocate(m);}
wzArrayBody::wzArrayBody(wzArrayBody& a, wzIndex off)
:Base(0),Max(0),Index(0),From(0)
{reinitialize(a,off);}
void wzArrayBody::reinitialize(wzArrayBody& a, wzIndex off)
{reinitialize();
if(!a.From){
throw wzFailure("components of separate arrays are not supported");
}
a.From->defineComponent(this,a.Index,off);
}
wzArrayBody::~wzArrayBody()
{reinitialize();}
void wzArrayBody::reinitialize()
{if(From) From->destroyArray(Index); else Allocate(0);}
wzBoolean wzArrayBody::require(wzIndex i)
{if(From) return From->Allocate(i+1);
else return allocate(Base,Max,i+1,Shift);
}
wzBoolean wzMemoryAllocation::allocate(wzByte*& base,
wzIndex& num, wzIndex min, wzIndex fac)
{wzIndex max = DefaultStrategy.suggested(min,num);
wzAddress adr=0;
if(fac==0){num=max; return wzTrue;}
if(base){
if(min==0){
#ifdef wzArrayTraceAllocation
cerr << " released\n";
#endif
wzArrayStaticInitializationManager::AllocationCount--;
free(base); base = 0; num = 0; return wzTrue;
}
adr = realloc(base,(max+1)*fac);
#ifdef wzArrayTraceAllocation
cerr << " reallocated: "<< max*fac<< " bytes\n";
#endif
if(adr) {base = (wzByte*)adr; num = max; return wzTrue;}
#ifdef wzArrayTraceAllocation
cerr << "not successful, second attempt: "<< min*fac
<< " bytes\n";
#endif
adr = realloc(base,min*fac);
if(adr) {base = (wzByte*)adr; num = min; return wzTrue;}
#ifdef wzArrayTraceAllocation
cerr << " not reallocated\n";
#endif
return wzFalse;
}else{
if(max==0) return wzTrue;
wzArrayStaticInitializationManager::AllocationCount++;
{int size = (max+1)*fac;
adr = malloc(size);
}
#ifdef wzArrayTraceAllocation
cerr << " allocated: "<< max*fac<< " bytes\n";
#endif
if(adr) {base = (wzByte*)adr; num = max; return wzTrue;}
adr = malloc(min*fac);
#ifdef wzArrayTraceAllocation
cerr << "not successful, second attempt: "<< min*fac
<< " bytes\n";
#endif
if(adr) {base = (wzByte*)adr; num = min; return wzTrue;}
#ifdef wzArrayTraceAllocation
cerr << " not allocated\n";
#endif
return wzFalse;
}
}
wzAllocationStrategy::~wzAllocationStrategy()
{;}
wzIndex wzAllocationStrategy::suggested(wzIndex min, wzIndex old)
{wzIndex i=min;
if(i==0) return 0;
if(old){
if(i<old+MinimalAdditionalSize) i=old+MinimalAdditionalSize;
if(i<(wzIndex)(MinimalFactor*old))i=(wzIndex)(MinimalFactor*old);
}else{
if(i<MinimalSize) i=MinimalSize;
}
if(Multiple>1) i = ((i/Multiple) + 1) * Multiple - 1;
return i;
}
// implementation of wzMultipleArrayController:
const wzIndex wzMultipleArrayController::TypeUndefined = 1;
const wzIndex wzMultipleArrayController::TypeSeparate = 2;
const wzIndex wzMultipleArrayController::TypeComponent = 3;
wzMultipleArrayController::wzMultipleArrayController(wzIndex max)
:Offset(1,max),Field(1,max),Base(1,max),Type(1,max),Max(max),Last(0),Free(0)
{;}
wzMultipleArrayController::~wzMultipleArrayController()
{wzIndex k;
for(k=1;k<=Last;k++){
destroyArray(k);
}
Last=Free=0;
}
wzIndex wzMultipleArrayController::defineArray(wzArrayBody* a)
{wzIndex f;
if(Free) {f=Free,Free=Base[Free];}
else {f=++Last;}
Type (f) = TypeSeparate;
Field(f) = a;
Base(f) = 0;
Offset(f) = 0;
a->From = this;
a->Index = f;
if(Max) a->Allocate(Max);
return f;
}
wzIndex wzMultipleArrayController::defineComponent(wzArrayBody *a,
wzIndex base, wzIndex off)
{wzIndex f;
if(Free) {f=Free,Free=Base[Free];}
else {f=++Last;}
Type (f) = TypeComponent;
Field(f) = a;
if(Type(base)==TypeSeparate){
Base (f) = base;
Offset(f) = off;
}else if (Type(base)==TypeComponent){
Base(f) = Base(base);
Offset(f) = Offset(base) + off;
}else {throw wzFailure("incorrect base array of a component");}
a->Base = Field[base]->Base + off; // sicher ist sicher
a->Shift = Field[base]->Shift;
a->Max = Field[base]->Max;
a->From = this;
a->Index = f;
return f;
}
void wzMultipleArrayController::destroyArray(wzIndex f)
{
if (Type(f)== TypeSeparate){
for(wzIndex k=1;k<=Last;k++){
if(Type[k]==TypeComponent && Base[k]==f) destroyArray(k);
}
Field[f]->Allocate(0);
}else if (Type(f)== TypeComponent){ Field[f]->Base = 0;
}else return;
Field[f]->From = 0;
Field[f]->Index = 0;
Field[f]->Max = 0;
Type[f] = TypeUndefined;
Field[f] = 0;
Base[f] = Free; Free = f;
}
wzBoolean wzMultipleArrayController::Allocate(wzIndex i)
{wzIndex k,m=0,m0;
for(k=1;k<=Last;k++) if(Type[k]==TypeSeparate){
Field[k]->Allocate(i);
m0 = Field[k]->Max;
if(m==0 || m>m0) m=m0;
}
for(k=1;k<=Last;k++) if(Type[k]==TypeComponent){
Field[k]->Base = Field[Base[k]]->Base + Offset[k];
Field[k]->Max = Field[Base[k]]->Max;
}
Max = m;
if(m>=i) return wzTrue; else return wzFalse;
}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?