📄 table.cpp
字号:
{
m_Index = (int *)SG_Realloc(m_Index, (m_nRecords + 1) * sizeof(int));
m_Index[m_nRecords] = m_nRecords;
}
//-----------------------------------------------------
m_Records[m_nRecords] = pRecord = new CSG_Table_Record(this, m_nRecords);
m_nRecords++;
//-----------------------------------------------------
if( pValues )
{
pRecord->Assign(pValues);
}
Set_Modified();
_Range_Invalidate();
return( pRecord );
}
//---------------------------------------------------------
CSG_Table_Record * CSG_Table::Ins_Record(int iRecord, CSG_Table_Record *pValues)
{
return( is_Private() ? NULL : _Ins_Record(iRecord, pValues) );
}
CSG_Table_Record * CSG_Table::_Ins_Record(int iRecord, CSG_Table_Record *pValues)
{
//-----------------------------------------------------
if( iRecord >= m_nRecords )
{
return( _Add_Record(pValues) );
}
else if( iRecord < 0 )
{
iRecord = 0;
}
//-----------------------------------------------------
if( (m_nRecords % GET_GROW_SIZE(m_nRecords)) == 0 )
{
CSG_Table_Record **pRecords = (CSG_Table_Record **)SG_Realloc(m_Records, (m_nRecords + GET_GROW_SIZE(m_nRecords)) * sizeof(CSG_Table_Record *));
if( pRecords == NULL )
{
return( NULL );
}
m_Records = pRecords;
}
//-----------------------------------------------------
int i;
CSG_Table_Record *pRecord;
if( is_Indexed() )
{
m_Index = (int *)SG_Realloc(m_Index, (m_nRecords + 1) * sizeof(int));
for(i=m_nRecords; i>iRecord; i--)
{
m_Index[i] = m_Index[i - 1];
}
m_Index[iRecord] = iRecord;
}
//-----------------------------------------------------
for(i=m_nRecords; i>iRecord; i--)
{
m_Records[i] = m_Records[i - 1];
m_Records[i]->m_Index = i;
}
m_Records[iRecord] = pRecord = new CSG_Table_Record(this, iRecord);
m_nRecords++;
//-----------------------------------------------------
if( pValues )
{
pRecord->Assign(pValues);
}
Set_Modified();
_Range_Invalidate();
return( pRecord );
}
//---------------------------------------------------------
bool CSG_Table::Del_Record(int iRecord)
{
return( is_Private() ? false : _Del_Record(iRecord) );
}
bool CSG_Table::_Del_Record(int iRecord)
{
int i, j;
if( iRecord >= 0 && iRecord < m_nRecords )
{
delete(m_Records[iRecord]);
m_nRecords--;
for(i=iRecord, j=iRecord+1; i<m_nRecords; i++, j++)
{
m_Records[i] = m_Records[i + 1];
m_Records[i]->m_Index = i;
}
m_Records = (CSG_Table_Record **)SG_Realloc(m_Records, m_nRecords * sizeof(CSG_Table_Record *));
if( is_Indexed() )
{
for(i=0; i<m_nRecords; i++)
{
if( m_Index[i] == iRecord )
{
for(; i<m_nRecords; i++)
{
m_Index[i] = m_Index[i + 1];
}
}
}
m_Index = (int *)SG_Realloc(m_Index, m_nRecords * sizeof(int));
for(i=0; i<m_nRecords; i++)
{
if( m_Index[i] > iRecord )
{
m_Index[i]--;
}
}
}
Set_Modified();
_Range_Invalidate();
return( true );
}
return( false );
}
//---------------------------------------------------------
bool CSG_Table::Del_Records(void)
{
return( is_Private() ? false : _Del_Records() );
}
bool CSG_Table::_Del_Records(void)
{
if( m_nRecords > 0 )
{
_Index_Destroy();
for(int iRecord=0; iRecord<m_nRecords; iRecord++)
{
delete(m_Records[iRecord]);
}
SG_Free(m_Records);
m_Records = NULL;
m_nRecords = 0;
return( true );
}
return( false );
}
///////////////////////////////////////////////////////////
// //
// Value Access //
// //
///////////////////////////////////////////////////////////
//---------------------------------------------------------
bool CSG_Table::Set_Value(int iRecord, int iField, const SG_Char *Value)
{
CSG_Table_Record *pRecord;
if( iField >= 0 && iField < m_nFields && (pRecord = Get_Record(iRecord)) != NULL )
{
return( pRecord->Set_Value(iField, Value) );
}
return( false );
}
//---------------------------------------------------------
bool CSG_Table::Set_Value(int iRecord, int iField, double Value)
{
CSG_Table_Record *pRecord;
if( iField >= 0 && iField < m_nFields && (pRecord = Get_Record(iRecord)) != NULL )
{
return( pRecord->Set_Value(iField, Value) );
}
return( false );
}
//---------------------------------------------------------
bool CSG_Table::Get_Value(int iRecord, int iField, CSG_String &Value) const
{
CSG_Table_Record *pRecord;
if( iField >= 0 && iField < m_nFields && (pRecord = Get_Record(iRecord)) != NULL )
{
Value = pRecord->asString(iField);
return( true );
}
return( false );
}
//---------------------------------------------------------
bool CSG_Table::Get_Value(int iRecord, int iField, double &Value) const
{
CSG_Table_Record *pRecord;
if( iField >= 0 && iField < m_nFields && (pRecord = Get_Record(iRecord)) != NULL )
{
Value = pRecord->asDouble(iField);
return( true );
}
return( false );
}
///////////////////////////////////////////////////////////
// //
// Statistics //
// //
///////////////////////////////////////////////////////////
//---------------------------------------------------------
bool CSG_Table::_Range_Invalidate(void) const
{
int iField;
for(iField=0; iField<m_nFields; iField++)
{
_Range_Invalidate(iField);
}
return( true );
}
//---------------------------------------------------------
bool CSG_Table::_Range_Invalidate(int iField) const
{
if( iField >= 0 && iField < m_nFields )
{
m_Field_Val_Min[iField] = 0.0;
m_Field_Val_Max[iField] = -1.0;
return( true );
}
return( false );
}
//---------------------------------------------------------
bool CSG_Table::_Range_Update(int iField) const
{
int iRecord;
double Value;
CSG_Table_Record **ppRecord;
if( iField >= 0 && iField < m_nFields && m_nRecords > 0 )
{
if( m_Field_Val_Min[iField] > m_Field_Val_Max[iField] )
{
ppRecord = m_Records;
m_Field_Val_Min[iField] = m_Field_Val_Max[iField] = (*ppRecord)->asDouble(iField);
for(iRecord=1, ppRecord++; iRecord<m_nRecords; iRecord++, ppRecord++)
{
Value = (*ppRecord)->asDouble(iField);
if( m_Field_Val_Min[iField] > Value )
{
m_Field_Val_Min[iField] = Value;
}
else if( m_Field_Val_Max[iField] < Value )
{
m_Field_Val_Max[iField] = Value;
}
}
}
return( true );
}
return( false );
}
///////////////////////////////////////////////////////////
// //
// Index //
// //
///////////////////////////////////////////////////////////
//---------------------------------------------------------
bool CSG_Table::Set_Index(int iField, TSG_Table_Index_Order Order)
{
if( iField >= 0 && iField < m_nFields )
{
m_Index_Order = Order;
switch( m_Index_Order )
{
case TABLE_INDEX_None: default:
_Index_Destroy();
break;
case TABLE_INDEX_Up:
case TABLE_INDEX_Down:
_Index_Create(iField);
break;
}
}
return( is_Indexed() );
}
//---------------------------------------------------------
bool CSG_Table::Toggle_Index(int iField)
{
if( iField >= 0 && iField < m_nFields )
{
if( iField != m_Index_Field )
{
return( Set_Index(iField, TABLE_INDEX_Up) );
}
else switch( m_Index_Order )
{
case TABLE_INDEX_None:
return( Set_Index(iField, TABLE_INDEX_Up) );
case TABLE_INDEX_Up:
return( Set_Index(iField, TABLE_INDEX_Down) );
case TABLE_INDEX_Down:
return( Set_Index(iField, TABLE_INDEX_None) );
}
}
return( false );
}
//---------------------------------------------------------
#define SORT_SWAP(a,b) {itemp=(a);(a)=(b);(b)=itemp;}
void CSG_Table::_Index_Create(int iField)
{
const int M = 7;
int indxt, itemp, *istack,
i, j, k, a,
l = 0,
ir = m_nRecords - 1,
nstack = 64,
jstack = 0;
//-----------------------------------------------------
m_Index_Field = iField;
if( m_Index == NULL )
{
m_Index = (int *)SG_Malloc(m_nRecords * sizeof(int));
}
for(j=0; j<m_nRecords; j++)
{
m_Index[j] = j;
}
istack = (int *)SG_Malloc(nstack * sizeof(int));
//-----------------------------------------------------
for(;;)
{
if( ir - l < M )
{
for(j=l+1; j<=ir; j++)
{
a = indxt = m_Index[j];
for(i=j-1; i>=0; i--)
{
if( _Index_Compare(m_Index[i], a) <= 0 )
{
break;
}
m_Index[i + 1] = m_Index[i];
}
m_Index[i + 1] = indxt;
}
if( jstack == 0 )
{
break;
}
ir = istack[jstack--];
l = istack[jstack--];
}
else
{
k = (l + ir) >> 1;
SORT_SWAP(m_Index[k], m_Index[l + 1]);
if( _Index_Compare(m_Index[l + 1], m_Index[ir]) > 0 )
SORT_SWAP( m_Index[l + 1], m_Index[ir]);
if( _Index_Compare(m_Index[l ], m_Index[ir]) > 0 )
SORT_SWAP( m_Index[l ], m_Index[ir]);
if( _Index_Compare(m_Index[l + 1], m_Index[l ]) > 0 )
SORT_SWAP( m_Index[l + 1], m_Index[l ]);
i = l + 1;
j = ir;
a = indxt = m_Index[l];
for(;;)
{
do i++; while( _Index_Compare(m_Index[i], a) < 0 );
do j--; while( _Index_Compare(m_Index[j], a) > 0 );
if( j < i )
{
break;
}
SORT_SWAP(m_Index[i], m_Index[j]);
}
m_Index[l] = m_Index[j];
m_Index[j] = indxt;
jstack += 2;
if( jstack >= nstack )
{
nstack += 64;
istack = (int *)SG_Realloc(istack, nstack * sizeof(int));
}
if( ir - i + 1 >= j - l )
{
istack[jstack] = ir;
istack[jstack - 1] = i;
ir = j - 1;
}
else
{
istack[jstack] = j - 1;
istack[jstack - 1] = l;
l = i;
}
}
}
SG_Free(istack);
}
#undef SORT_SWAP
//---------------------------------------------------------
void CSG_Table::_Index_Destroy(void)
{
m_Index_Field = -1;
m_Index_Order = TABLE_INDEX_None;
if( m_Index )
{
SG_Free(m_Index);
m_Index = NULL;
}
}
//---------------------------------------------------------
inline int CSG_Table::_Index_Compare(int a, int b)
{
switch( m_Field_Type[m_Index_Field] )
{
case TABLE_FIELDTYPE_String:
return( SG_STR_CMP(
m_Records[a]->asString(m_Index_Field),
m_Records[b]->asString(m_Index_Field))
);
default:
double d = m_Records[a]->asDouble(m_Index_Field)
- m_Records[b]->asDouble(m_Index_Field);
return( d < 0.0 ? -1 : (d > 0.0 ? 1 : 0) );
}
}
///////////////////////////////////////////////////////////
// //
// //
// //
///////////////////////////////////////////////////////////
//---------------------------------------------------------
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -