SAGA API  v9.5
table.cpp
Go to the documentation of this file.
1 
3 // //
4 // SAGA //
5 // //
6 // System for Automated Geoscientific Analyses //
7 // //
8 // Application Programming Interface //
9 // //
10 // Library: SAGA_API //
11 // //
12 //-------------------------------------------------------//
13 // //
14 // table.cpp //
15 // //
16 // Copyright (C) 2005 by Olaf Conrad //
17 // //
18 //-------------------------------------------------------//
19 // //
20 // This file is part of 'SAGA - System for Automated //
21 // Geoscientific Analyses'. //
22 // //
23 // This library is free software; you can redistribute //
24 // it and/or modify it under the terms of the GNU Lesser //
25 // General Public License as published by the Free //
26 // Software Foundation, either version 2.1 of the //
27 // License, or (at your option) any later version. //
28 // //
29 // This library is distributed in the hope that it will //
30 // be useful, but WITHOUT ANY WARRANTY; without even the //
31 // implied warranty of MERCHANTABILITY or FITNESS FOR A //
32 // PARTICULAR PURPOSE. See the GNU Lesser General Public //
33 // License for more details. //
34 // //
35 // You should have received a copy of the GNU Lesser //
36 // General Public License along with this program; if //
37 // not, see <http://www.gnu.org/licenses/>. //
38 // //
39 //-------------------------------------------------------//
40 // //
41 // contact: Olaf Conrad //
42 // Institute of Geography //
43 // University of Goettingen //
44 // Goldschmidtstr. 5 //
45 // 37077 Goettingen //
46 // Germany //
47 // //
48 // e-mail: oconrad@saga-gis.org //
49 // //
51 
52 //---------------------------------------------------------
53 #include "table.h"
54 #include "shapes.h"
55 #include "tool_library.h"
56 
57 
59 // //
60 // //
61 // //
63 
64 //---------------------------------------------------------
66 {
67  return( new CSG_Table );
68 }
69 
70 //---------------------------------------------------------
72 {
73  switch( Table.Get_ObjectType() )
74  {
76  return( new CSG_Table(Table) );
77 
80  return( SG_Create_Shapes(*((CSG_Shapes *)&Table)) );
81 
82  default:
83  return( NULL );
84  }
85 }
86 
87 //---------------------------------------------------------
89 {
90  if( pTemplate )
91  {
92  switch( pTemplate->Get_ObjectType() )
93  {
95  return( new CSG_Table(pTemplate) );
96 
99  return( SG_Create_Shapes((CSG_Shapes *)pTemplate) );
100 
101  default:
102  break;
103  }
104  }
105 
106  return( new CSG_Table() );
107 }
108 
109 //---------------------------------------------------------
110 CSG_Table * SG_Create_Table(const char *File, TSG_Table_File_Type Format, int Encoding) { return( SG_Create_Table(CSG_String(File), Format, Encoding) ); }
111 CSG_Table * SG_Create_Table(const wchar_t *File, TSG_Table_File_Type Format, int Encoding) { return( SG_Create_Table(CSG_String(File), Format, Encoding) ); }
112 CSG_Table * SG_Create_Table(const CSG_String &File, TSG_Table_File_Type Format, int Encoding)
113 {
114  return( new CSG_Table(File, Format, Encoding) );
115 }
116 
117 //---------------------------------------------------------
118 CSG_Table * SG_Create_Table(const char *File, TSG_Table_File_Type Format, const SG_Char Separator, int Encoding) { return( SG_Create_Table(CSG_String(File), Format, Separator, Encoding) ); }
119 CSG_Table * SG_Create_Table(const wchar_t *File, TSG_Table_File_Type Format, const SG_Char Separator, int Encoding) { return( SG_Create_Table(CSG_String(File), Format, Separator, Encoding) ); }
120 CSG_Table * SG_Create_Table(const CSG_String &File, TSG_Table_File_Type Format, const SG_Char Separator, int Encoding)
121 {
122  return( new CSG_Table(File, Format, Encoding) );
123 }
124 
125 
127 // //
128 // //
129 // //
131 
132 //---------------------------------------------------------
134  : CSG_Data_Object()
135 {
137 }
138 
140 {
141  Destroy(); return( true );
142 }
143 
144 //---------------------------------------------------------
146  : CSG_Data_Object()
147 {
148  _On_Construction(); Create(Table);
149 }
150 
151 bool CSG_Table::Create(const CSG_Table &Table)
152 {
153  return( Assign((CSG_Data_Object *)&Table) );
154 }
155 
156 //---------------------------------------------------------
157 CSG_Table::CSG_Table(const char *File, TSG_Table_File_Type Format, int Encoding) : CSG_Table(CSG_String(File), Format, Encoding) {}
158 CSG_Table::CSG_Table(const wchar_t *File, TSG_Table_File_Type Format, int Encoding) : CSG_Table(CSG_String(File), Format, Encoding) {}
159 CSG_Table::CSG_Table(const CSG_String &File, TSG_Table_File_Type Format, int Encoding)
160  : CSG_Data_Object()
161 {
162  _On_Construction(); Create(File, Format, Encoding);
163 }
164 
165 bool CSG_Table::Create(const char *File, TSG_Table_File_Type Format, int Encoding) { return( Create(CSG_String(File), Format, Encoding) ); }
166 bool CSG_Table::Create(const wchar_t *File, TSG_Table_File_Type Format, int Encoding) { return( Create(CSG_String(File), Format, Encoding) ); }
167 bool CSG_Table::Create(const CSG_String &File, TSG_Table_File_Type Format, int Encoding)
168 {
169  Destroy();
170 
171  SG_UI_Msg_Add(CSG_String::Format("%s %s: %s...", _TL("Loading"), _TL("table"), File.c_str()), true);
172 
173  //-----------------------------------------------------
174  bool bResult = File.BeforeFirst(':').Cmp("PGSQL") && SG_File_Exists(File) && Load(File, (int)Format, '\0', Encoding);
175 
176  if( bResult )
177  {
178  Set_File_Name(File, true);
179  }
180 
181  //-----------------------------------------------------
182  else if( File.BeforeFirst(':').Cmp("PGSQL") == 0 ) // database source
183  {
184  CSG_String s(File);
185 
186  s = s.AfterFirst(':'); CSG_String Host (s.BeforeFirst(':'));
187  s = s.AfterFirst(':'); CSG_String Port (s.BeforeFirst(':'));
188  s = s.AfterFirst(':'); CSG_String DBName(s.BeforeFirst(':'));
189  s = s.AfterFirst(':'); CSG_String Table (s.BeforeFirst(':'));
190 
191  CSG_Tool *pTool = SG_Get_Tool_Library_Manager().Create_Tool("db_pgsql", 0, true); // CGet_Connections
192 
193  if( pTool != NULL )
194  {
196 
197  //---------------------------------------------
198  CSG_Table Connections; CSG_String Connection(DBName + " [" + Host + ":" + Port + "]");
199 
200  pTool->Set_Manager(NULL); pTool->On_Before_Execution();
201 
202  if( SG_TOOL_PARAMETER_SET("CONNECTIONS", &Connections) && pTool->Execute() ) // CGet_Connections
203  {
204  for(int i=0; !bResult && i<Connections.Get_Count(); i++)
205  {
206  if( !Connection.Cmp(Connections[i].asString(0)) )
207  {
208  bResult = true;
209  }
210  }
211  }
212 
214 
215  //---------------------------------------------
216  if( bResult && (bResult = (pTool = SG_Get_Tool_Library_Manager().Create_Tool("db_pgsql", 12, true)) != NULL) == true ) // CPGIS_Table_Load
217  {
218  pTool->Set_Manager(NULL); pTool->On_Before_Execution();
219 
220  bResult = SG_TOOL_PARAMETER_SET("CONNECTION", Connection)
221  && SG_TOOL_PARAMETER_SET("DB_TABLE" , Table )
222  && SG_TOOL_PARAMETER_SET("TABLE" , this )
223  && pTool->Execute();
224 
226  }
227 
229  }
230  }
231 
232  //-----------------------------------------------------
233  if( bResult )
234  {
235  Set_Modified(false);
236  Set_Update_Flag();
237 
238  SG_UI_Msg_Add(_TL("okay"), false, SG_UI_MSG_STYLE_SUCCESS);
239 
240  return( true );
241  }
242 
243  Destroy();
244 
245  SG_UI_Msg_Add(_TL("failed"), false, SG_UI_MSG_STYLE_FAILURE);
246 
247  return( false );
248 }
249 
250 //---------------------------------------------------------
251 CSG_Table::CSG_Table(const char *File, TSG_Table_File_Type Format, const SG_Char Separator, int Encoding) : CSG_Table(CSG_String(File), Format, Separator, Encoding) {}
252 CSG_Table::CSG_Table(const wchar_t *File, TSG_Table_File_Type Format, const SG_Char Separator, int Encoding) : CSG_Table(CSG_String(File), Format, Separator, Encoding) {}
253 CSG_Table::CSG_Table(const CSG_String &File, TSG_Table_File_Type Format, const SG_Char Separator, int Encoding)
254  : CSG_Data_Object()
255 {
256  _On_Construction(); Create(File, Format, Separator, Encoding);
257 }
258 
259 bool CSG_Table::Create(const char *File, TSG_Table_File_Type Format, const SG_Char Separator, int Encoding) { return( Create(CSG_String(File), Format, Separator, Encoding) ); }
260 bool CSG_Table::Create(const wchar_t *File, TSG_Table_File_Type Format, const SG_Char Separator, int Encoding) { return( Create(CSG_String(File), Format, Separator, Encoding) ); }
261 bool CSG_Table::Create(const CSG_String &File, TSG_Table_File_Type Format, const SG_Char Separator, int Encoding)
262 {
263  return( Load(File, (int)Format, Separator, Encoding) );
264 }
265 
266 //---------------------------------------------------------
268  : CSG_Data_Object()
269 {
270  _On_Construction(); Create(pTemplate);
271 }
272 
273 bool CSG_Table::Create(const CSG_Table *pTemplate)
274 {
275  if( !pTemplate || pTemplate->Get_Field_Count() < 1 )
276  {
277  return( false );
278  }
279 
280  Destroy();
281 
282  Set_Name (pTemplate->Get_Name ());
283  Set_Description (pTemplate->Get_Description());
284  Set_NoData_Value_Range(pTemplate->Get_NoData_Value(), pTemplate->Get_NoData_Value(true));
285 
286  m_Encoding = pTemplate->m_Encoding;
287 
288  for(int i=0; i<pTemplate->Get_Field_Count(); i++)
289  {
290  Add_Field(pTemplate->Get_Field_Name(i), pTemplate->Get_Field_Type(i));
291  }
292 
293  return( true );
294 }
295 
296 
298 // //
300 
301 //---------------------------------------------------------
303 {
304  m_nFields = 0;
305  m_Field_Name = NULL;
306  m_Field_Type = NULL;
307  m_Field_Stats = NULL;
308 
309  m_Records = NULL;
310  m_nRecords = 0;
311  m_nBuffer = 0;
312 
314 
315  m_Selection.Create(sizeof(sLong), 0, TSG_Array_Growth::SG_ARRAY_GROWTH_3);
316 
317  Set_Update_Flag();
318 }
319 
320 
322 // //
324 
325 //---------------------------------------------------------
327 {
328  Destroy();
329 }
330 
331 //---------------------------------------------------------
333 {
334  _Destroy_Selection();
335 
336  Del_Records();
337 
338  if( m_nFields > 0 )
339  {
340  for(int i=0; i<m_nFields; i++)
341  {
342  delete(m_Field_Name [i]);
343  delete(m_Field_Stats[i]);
344  }
345 
349 
350  m_nFields = 0;
351  m_Field_Name = NULL;
352  m_Field_Type = NULL;
353  m_Field_Stats = NULL;
354  }
355 
357 
358  return( true );
359 }
360 
361 
363 // //
364 // Assign //
365 // //
367 
368 //---------------------------------------------------------
370 {
371  Create(Table);
372 
373  return( *this );
374 }
375 
376 //---------------------------------------------------------
378 {
379  if( CSG_Data_Object::Assign(pObject) && pObject->asTable(true) && Create(pObject->asTable(true)) )
380  {
381  CSG_Table *pTable = pObject->asTable(true);
382 
383  for(sLong i=0; i<pTable->Get_Count(); i++)
384  {
385  Add_Record(pTable->Get_Record(i));
386  }
387 
388  return( true );
389  }
390 
391  return( false );
392 }
393 
394 //---------------------------------------------------------
396 {
397  if( is_Compatible(Table) && Set_Count(Table.Get_Count()) )
398  {
399  for(sLong i=0; i<Table.Get_Count(); i++)
400  {
401  Get_Record(i)->Assign(Table.Get_Record(i));
402  }
403 
404  return( true );
405  }
406 
407  return( false );
408 }
409 
410 //---------------------------------------------------------
412 {
413  return( pTable && Assign_Values(*pTable) );
414 }
415 
416 //---------------------------------------------------------
417 bool CSG_Table::Assign_Values(const SG_Char *FileName)
418 {
419  CSG_Table Table; return( Table.Create(FileName) && Assign_Values(&Table) );
420 }
421 
422 
424 // //
425 // Checks //
426 // //
428 
429 //---------------------------------------------------------
430 bool CSG_Table::is_Compatible(const CSG_Table &Table, bool bExactMatch) const
431 {
432  if( Get_Field_Count() == Table.Get_Field_Count() )
433  {
434  for(int i=0; i<Get_Field_Count(); i++)
435  {
436  if( bExactMatch )
437  {
438  if( Get_Field_Type(i) != Table.Get_Field_Type(i) )
439  {
440  return( false );
441  }
442  }
443  else switch( Get_Field_Type(i) )
444  {
445  case SG_DATATYPE_String:
446  // if( Table.Get_Field_Type(i) != SG_DATATYPE_String )
447  // {
448  // return( false );
449  // }
450  break;
451 
452  default:
453  if( Table.Get_Field_Type(i) == SG_DATATYPE_String )
454  {
455  return( false );
456  }
457  break;
458  }
459  }
460 
461  return( true );
462  }
463 
464  return( false );
465 }
466 
467 //---------------------------------------------------------
468 bool CSG_Table::is_Compatible(CSG_Table *pTable, bool bExactMatch) const
469 {
470  return( pTable && is_Compatible(*pTable, bExactMatch) );
471 }
472 
473 
475 // //
476 // Fields //
477 // //
479 
480 //---------------------------------------------------------
481 bool CSG_Table::Add_Field(const CSG_String &Name, TSG_Data_Type Type, int Position)
482 {
483  if( Position < 0 || Position > m_nFields )
484  {
485  Position = m_nFields;
486  }
487 
488  //-----------------------------------------------------
489  m_nFields++;
490 
494 
495  //-----------------------------------------------------
496  for(int i=m_nFields-1; i>Position; i--)
497  {
498  m_Field_Name [i] = m_Field_Name [i - 1];
499  m_Field_Type [i] = m_Field_Type [i - 1];
500  m_Field_Stats[i] = m_Field_Stats[i - 1];
501  }
502 
503  //-----------------------------------------------------
504  m_Field_Name [Position] = new CSG_String(!Name.is_Empty() ? Name : CSG_String::Format("FIELD_%d", m_nFields));
505  m_Field_Type [Position] = Type;
506  m_Field_Stats[Position] = new CSG_Simple_Statistics();
507 
508  //-----------------------------------------------------
509  for(sLong i=0; i<m_nRecords; i++)
510  {
511  m_Records[i]->_Add_Field(Position);
512  }
513 
514  Set_Modified();
515 
516  return( true );
517 }
518 
519 //---------------------------------------------------------
520 bool CSG_Table::Del_Field(int del_Field)
521 {
522  if( del_Field < 0 || del_Field >= m_nFields )
523  {
524  return( false );
525  }
526 
527  //-----------------------------------------------------
528  delete(m_Field_Name [del_Field]);
529  delete(m_Field_Stats[del_Field]);
530 
531  //-------------------------------------------------
532  m_nFields--;
533 
534  for(int i=del_Field; i<m_nFields; i++)
535  {
536  m_Field_Name [i] = m_Field_Name [i + 1];
537  m_Field_Type [i] = m_Field_Type [i + 1];
538  m_Field_Stats[i] = m_Field_Stats[i + 1];
539  }
540 
541  //-------------------------------------------------
545 
546  //-------------------------------------------------
547  for(sLong i=0; i<m_nRecords; i++)
548  {
549  m_Records[i]->_Del_Field(del_Field);
550  }
551 
552  Set_Modified();
553 
554  return( true );
555 }
556 
557 //---------------------------------------------------------
558 bool CSG_Table::Mov_Field(int iField, int Position)
559 {
560  if( Position < 0 )
561  {
562  Position = 0;
563  }
564  else if( Position >= m_nFields - 1 )
565  {
566  Position = m_nFields - 1;
567  }
568 
569  if( iField < 0 || iField >= m_nFields || iField == Position )
570  {
571  return( false );
572  }
573 
574  //-----------------------------------------------------
575  if( Position > iField )
576  {
577  Position++;
578  }
579 
580  if( !Add_Field(Get_Field_Name(iField), Get_Field_Type(iField), Position) )
581  {
582  return( false );
583  }
584 
585  if( Position < iField )
586  {
587  iField++;
588  }
589 
590  #pragma omp parallel for
591  for(sLong i=0; i<m_nRecords; i++)
592  {
593  *m_Records[i]->Get_Value(Position) = *m_Records[i]->Get_Value(iField);
594  }
595 
596  if( !Del_Field(iField) )
597  {
598  return( false );
599  }
600 
601  //-----------------------------------------------------
602  return( true );
603 }
604 
605 
607 // //
609 
610 //---------------------------------------------------------
611 bool CSG_Table::Set_Field_Name(int iField, const SG_Char *Name)
612 {
613  if( iField >= 0 && iField < m_nFields && Name && *Name )
614  {
615  *(m_Field_Name[iField]) = Name;
616 
617  Set_Modified();
618 
619  return( true );
620  }
621 
622  return( false );
623 }
624 
625 //---------------------------------------------------------
627 {
628  if( iField < 0 || iField >= m_nFields )
629  {
630  return( false );
631  }
632 
633  if( m_Field_Type[iField] == Type )
634  {
635  return( true );
636  }
637 
638  m_Field_Type[iField] = Type;
639 
640  for(sLong i=0; i<m_nRecords; i++)
641  {
642  CSG_Table_Record *pRecord = m_Records[i];
643 
645 
646  (*pValue) = *pRecord->m_Values[iField];
647 
648  delete(pRecord->m_Values[iField]);
649 
650  pRecord->m_Values[iField] = pValue;
651 
652  pRecord->Set_Modified();
653  }
654 
655  return( true );
656 }
657 
658 //---------------------------------------------------------
659 int CSG_Table::Get_Field_Length(int iField, int Encoding) const
660 {
661  size_t Length = 0;
662 
663  if( iField >= 0 && iField < m_nFields && m_Field_Type[iField] == SG_DATATYPE_String )
664  {
665  for(sLong i=0; i<m_nRecords; i++)
666  {
667  CSG_String s(m_Records[i]->asString(iField));
668 
669  size_t nBytes;
670 
671  switch( Encoding )
672  {
673  default :
674  case SG_FILE_ENCODING_UTF7 : nBytes = s.Length() ; break;
675  case SG_FILE_ENCODING_UTF8 : nBytes = s.to_UTF8().Get_Size(); break;
677  case SG_FILE_ENCODING_UTF16BE: nBytes = s.Length() * 2 ; break;
679  case SG_FILE_ENCODING_UTF32BE: nBytes = s.Length() * 4 ; break;
680  }
681 
682  if( Length < nBytes )
683  {
684  Length = nBytes;
685  }
686  }
687  }
688 
689  return( (int)Length );
690 }
691 
692 //---------------------------------------------------------
693 int CSG_Table::Get_Field(const char *Name) const { return( Get_Field(CSG_String(Name))); }
694 int CSG_Table::Get_Field(const wchar_t *Name) const { return( Get_Field(CSG_String(Name))); }
695 int CSG_Table::Get_Field(const CSG_String &Name) const
696 {
697  for(int iField=0; iField<Get_Field_Count(); iField++)
698  {
699  if( !Name.Cmp(Get_Field_Name(iField)) )
700  {
701  return( iField );
702  }
703  }
704 
705  return( -1 );
706 }
707 
708 //---------------------------------------------------------
713 int CSG_Table::Find_Field(const CSG_String &Name) const
714 {
715  for(int i=0; i<Get_Field_Count(); i++)
716  {
717  if( !Name.Cmp(Get_Field_Name(i)) )
718  {
719  return( i );
720  }
721  }
722 
723  return( -1 );
724 }
725 
726 //---------------------------------------------------------
731 bool CSG_Table::Find_Field(const CSG_String &Name, int &Index) const
732 {
733  return( (Index = Find_Field(Name)) >= 0 );
734 }
735 
736 
738 // //
739 // Records //
740 // //
742 
743 //---------------------------------------------------------
744 #define GET_GROW_SIZE(n) (n < 256 ? 1 : (n < 8192 ? 128 : 1024))
745 
746 //---------------------------------------------------------
747 bool CSG_Table::_Inc_Array(void)
748 {
749  if( m_nRecords < m_nBuffer )
750  {
751  return( true );
752  }
753 
754  CSG_Table_Record **pRecords = (CSG_Table_Record **)SG_Realloc(m_Records, (m_nBuffer + GET_GROW_SIZE(m_nBuffer)) * sizeof(CSG_Table_Record *));
755 
756  if( pRecords == NULL )
757  {
758  return( false );
759  }
760 
761  m_Records = pRecords;
763 
764  return( true );
765 }
766 
767 //---------------------------------------------------------
768 bool CSG_Table::_Dec_Array(void)
769 {
770  if( m_nRecords < 0 || m_nRecords >= m_nBuffer - GET_GROW_SIZE(m_nBuffer) )
771  {
772  return( true );
773  }
774 
775  CSG_Table_Record **pRecords = (CSG_Table_Record **)SG_Realloc(m_Records, (m_nBuffer - GET_GROW_SIZE(m_nBuffer)) * sizeof(CSG_Table_Record *));
776 
777  if( pRecords == NULL )
778  {
779  return( false );
780  }
781 
782  m_Records = pRecords;
784 
785  return( true );
786 }
787 
788 //---------------------------------------------------------
790 {
791  return( new CSG_Table_Record(this, Index) );
792 }
793 
794 //---------------------------------------------------------
796 {
797  return( Ins_Record(m_nRecords, pCopy) );
798 }
799 
800 //---------------------------------------------------------
802 {
803  if( iRecord < 0 ) { iRecord = 0; } else if( iRecord > m_nRecords ) { iRecord = m_nRecords; }
804 
805  CSG_Table_Record *pRecord = _Inc_Array() ? _Get_New_Record(m_nRecords) : NULL;
806 
807  if( pRecord )
808  {
809  if( pCopy )
810  {
811  pRecord->Assign(pCopy);
812  }
813 
814  //-------------------------------------------------
815  if( iRecord < m_nRecords )
816  {
817  if( Get_Selection_Count() > 0 ) // update selection index
818  {
819  sLong *Selection = (sLong *)m_Selection.Get_Array();
820 
821  for(sLong i=0; i<m_Selection.Get_Size(); i++)
822  {
823  if( Selection[i] > iRecord )
824  {
825  Selection[i]++;
826  }
827  }
828  }
829 
830  for(sLong i=m_nRecords; i>iRecord; i--)
831  {
832  m_Records[i] = m_Records[i - 1]; m_Records[i]->m_Index = i;
833  }
834 
835  pRecord->m_Index = iRecord;
836  }
837 
838  m_Records[iRecord] = pRecord;
839  m_nRecords++;
840 
841  //-------------------------------------------------
842  if( m_Index.is_Okay() )
843  {
844  m_Index.Add_Entry(iRecord);
845  }
846 
847  Set_Modified();
848 
849  Set_Update_Flag();
850 
852  }
853 
854  return( pRecord );
855 }
856 
857 //---------------------------------------------------------
859 {
860  if( iRecord >= 0 && iRecord < m_nRecords && pCopy )
861  {
862  return( m_Records[iRecord]->Assign(pCopy) );
863  }
864 
865  return( false );
866 }
867 
868 //---------------------------------------------------------
870 {
871  if( iRecord >= 0 && iRecord < m_nRecords )
872  {
873  if( m_Records[iRecord]->is_Selected() )
874  {
875  _Del_Selection(iRecord);
876  }
877 
878  delete(m_Records[iRecord]);
879 
880  m_nRecords--;
881 
882  for(sLong i=iRecord; i<m_nRecords; i++)
883  {
884  m_Records[i] = m_Records[i + 1]; m_Records[i]->m_Index = i;
885  }
886 
887  _Dec_Array();
888 
889  //-------------------------------------------------
890  if( m_Index.is_Okay() )
891  {
892  m_Index.Del_Entry(iRecord);
893  }
894 
895  Set_Modified();
896 
897  Set_Update_Flag();
898 
900 
901  return( true );
902  }
903 
904  return( false );
905 }
906 
907 //---------------------------------------------------------
909 {
910  Del_Index();
911 
912  for(sLong iRecord=0; iRecord<m_nRecords; iRecord++)
913  {
914  delete(m_Records[iRecord]);
915  }
916 
917  SG_FREE_SAFE(m_Records);
918 
919  m_nRecords = 0;
920  m_nBuffer = 0;
921 
922  return( true );
923 }
924 
925 //---------------------------------------------------------
927 {
928  if( m_nRecords < nRecords )
929  {
930  while( m_nRecords < nRecords && Add_Record() != NULL ) {}
931  }
932  else if( nRecords >= 0 && m_nRecords > nRecords )
933  {
934  while( m_nRecords > nRecords && Del_Record(m_nRecords - 1) ) {}
935  }
936 
937  return( m_nRecords == nRecords );
938 }
939 
940 
942 // //
944 
945 //---------------------------------------------------------
946 bool CSG_Table::Find_Record(sLong &iRecord, int iField, const CSG_String &Value, bool bCreateIndex)
947 {
948  if( iField < 0 || iField >= m_nFields || m_nRecords < 1 )
949  {
950  return( false );
951  }
952 
953  if( m_nRecords == 1 )
954  {
955  return( Value.Cmp(m_Records[iRecord = 0]->asString(iField)) == 0 );
956  }
957 
958  if( bCreateIndex && iField != Get_Index_Field(0) )
959  {
961  }
962 
963  //-----------------------------------------------------
964  if( iField != Get_Index_Field(0) )
965  {
966  for(iRecord=0; iRecord<m_nRecords; iRecord++)
967  {
968  if( Value.Cmp(m_Records[iRecord]->asString(iField)) == 0 )
969  {
970  return( true );
971  }
972  }
973  }
974 
975  //-----------------------------------------------------
976  else // indexed search
977  {
978  #define GET_RECORD(i) Get_Record_byIndex(bAscending ? (iRecord = i) : m_nRecords - 1 - (iRecord = i))
979 
980  double d; bool bAscending = Get_Index_Order(0) == TABLE_INDEX_Ascending;
981 
982  if( (d = Value.Cmp(GET_RECORD(0 )->asString(iField))) < 0 ) { return( false ); } else if( d == 0 ) { return( true ); }
983  if( (d = Value.Cmp(GET_RECORD(m_nRecords - 1)->asString(iField))) > 0 ) { return( false ); } else if( d == 0 ) { return( true ); }
984 
985  for(sLong a=0, b=m_nRecords-1; b-a > 1; )
986  {
987  d = Value.Cmp(GET_RECORD(a + (b - a) / 2)->asString(iField));
988 
989  if( d > 0. )
990  {
991  a = iRecord;
992  }
993  else if( d < 0. )
994  {
995  b = iRecord;
996  }
997  else
998  {
999  iRecord = Get_Record_byIndex(bAscending ? iRecord : m_nRecords - 1 - iRecord)->Get_Index();
1000 
1001  return( true );
1002  }
1003  }
1004 
1005  iRecord = Get_Record_byIndex(bAscending ? iRecord : m_nRecords - 1 - iRecord)->Get_Index();
1006  }
1007 
1008  //-----------------------------------------------------
1009  return( false );
1010 }
1011 
1012 //---------------------------------------------------------
1013 CSG_Table_Record * CSG_Table::Find_Record(int iField, const CSG_String &Value, bool bCreateIndex)
1014 {
1015  sLong iRecord;
1016 
1017  if( Find_Record(iRecord, iField, Value, bCreateIndex) )
1018  {
1019  return( Get_Record(iRecord) );
1020  }
1021 
1022  return( NULL );
1023 }
1024 
1025 //---------------------------------------------------------
1026 bool CSG_Table::Find_Record(sLong &iRecord, int iField, double Value, bool bCreateIndex)
1027 {
1028  if( iField < 0 || iField >= m_nFields || m_nRecords < 1 )
1029  {
1030  return( false );
1031  }
1032 
1033  if( m_nRecords == 1 )
1034  {
1035  return( Value == m_Records[iRecord = 0]->asDouble(iField) );
1036  }
1037 
1038  if( bCreateIndex && iField != Get_Index_Field(0) )
1039  {
1041  }
1042 
1043  //-----------------------------------------------------
1044  if( iField != Get_Index_Field(0) )
1045  {
1046  for(iRecord=0; iRecord<m_nRecords; iRecord++)
1047  {
1048  if( Value == m_Records[iRecord]->asDouble(iField) )
1049  {
1050  return( true );
1051  }
1052  }
1053  }
1054 
1055  //-----------------------------------------------------
1056  else // indexed search
1057  {
1058  #define GET_RECORD(i) Get_Record_byIndex(bAscending ? (iRecord = i) : m_nRecords - 1 - (iRecord = i))
1059 
1060  double d; bool bAscending = Get_Index_Order(0) == TABLE_INDEX_Ascending;
1061 
1062  if( (d = Value - GET_RECORD(0 )->asDouble(iField)) < 0. ) { return( false ); } else if( d == 0. ) { return( true ); }
1063  if( (d = Value - GET_RECORD(m_nRecords - 1)->asDouble(iField)) > 0. ) { return( false ); } else if( d == 0. ) { return( true ); }
1064 
1065  for(sLong a=0, b=m_nRecords-1; b-a > 1; )
1066  {
1067  d = Value - GET_RECORD(a + (b - a) / 2)->asDouble(iField);
1068 
1069  if( d > 0. )
1070  {
1071  a = iRecord;
1072  }
1073  else if( d < 0. )
1074  {
1075  b = iRecord;
1076  }
1077  else
1078  {
1079  iRecord = Get_Record_byIndex(bAscending ? iRecord : m_nRecords - 1 - iRecord)->Get_Index();
1080 
1081  return( true );
1082  }
1083  }
1084 
1085  iRecord = Get_Record_byIndex(bAscending ? iRecord : m_nRecords - 1 - iRecord)->Get_Index();
1086  }
1087 
1088  //-----------------------------------------------------
1089  return( false );
1090 }
1091 
1092 //---------------------------------------------------------
1093 CSG_Table_Record * CSG_Table::Find_Record(int iField, double Value, bool bCreateIndex)
1094 {
1095  sLong iRecord;
1096 
1097  if( Find_Record(iRecord, iField, Value, bCreateIndex) )
1098  {
1099  return( Get_Record(iRecord) );
1100  }
1101 
1102  return( NULL );
1103 }
1104 
1105 
1107 // //
1108 // Value Access //
1109 // //
1111 
1112 //---------------------------------------------------------
1113 void CSG_Table::Set_Modified(bool bModified)
1114 {
1115  if( bModified != is_Modified() )
1116  {
1117  CSG_Data_Object::Set_Modified(bModified);
1118 
1119  if( bModified == false )
1120  {
1121  #pragma omp parallel for
1122  for(sLong iRecord=0; iRecord<m_nRecords; iRecord++)
1123  {
1124  m_Records[iRecord]->Set_Modified(false);
1125  }
1126  }
1127  }
1128 }
1129 
1130 //---------------------------------------------------------
1131 bool CSG_Table::Set_Value(sLong iRecord, int iField, const SG_Char *Value)
1132 {
1133  if( iField >= 0 && iField < m_nFields )
1134  {
1135  CSG_Table_Record *pRecord = Get_Record(iRecord);
1136 
1137  return( pRecord && pRecord->Set_Value(iField, Value) );
1138  }
1139 
1140  return( false );
1141 }
1142 
1143 //---------------------------------------------------------
1144 bool CSG_Table::Set_Value(sLong iRecord, int iField, double Value)
1145 {
1146  if( iField >= 0 && iField < m_nFields )
1147  {
1148  CSG_Table_Record *pRecord = Get_Record(iRecord);
1149 
1150  return( pRecord && pRecord->Set_Value(iField, Value) );
1151  }
1152 
1153  return( false );
1154 }
1155 
1156 //---------------------------------------------------------
1157 bool CSG_Table::Get_Value(sLong iRecord, int iField, CSG_String &Value) const
1158 {
1159  if( iField >= 0 && iField < m_nFields )
1160  {
1161  CSG_Table_Record *pRecord = Get_Record(iRecord);
1162 
1163  if( pRecord )
1164  {
1165  Value = pRecord->asString(iField);
1166 
1167  return( true );
1168  }
1169  }
1170 
1171  return( false );
1172 }
1173 
1174 //---------------------------------------------------------
1175 bool CSG_Table::Get_Value(sLong iRecord, int iField, double &Value) const
1176 {
1177  if( iField >= 0 && iField < m_nFields )
1178  {
1179  CSG_Table_Record *pRecord = Get_Record(iRecord);
1180 
1181  if( pRecord )
1182  {
1183  Value = pRecord->asDouble(iField);
1184 
1185  return( true );
1186  }
1187  }
1188 
1189  return( false );
1190 }
1191 
1192 
1194 // //
1195 // Statistics //
1196 // //
1198 
1199 //---------------------------------------------------------
1201 {
1202  for(int iField=0; iField<m_nFields; iField++)
1203  {
1204  m_Field_Stats[iField]->Invalidate();
1205  }
1206 
1207  return( true );
1208 }
1209 
1210 //---------------------------------------------------------
1211 bool CSG_Table::_Stats_Invalidate(int iField) const
1212 {
1213  if( iField >= 0 && iField < m_nFields )
1214  {
1215  m_Field_Stats[iField]->Invalidate();
1216 
1217  return( true );
1218  }
1219 
1220  return( false );
1221 }
1222 
1223 //---------------------------------------------------------
1224 bool CSG_Table::_Stats_Update(int iField) const
1225 {
1226  if( iField < 0 || iField >= m_nFields || Get_Count() < 1 )
1227  {
1228  return( false );
1229  }
1230 
1231  CSG_Simple_Statistics &Statistics = *m_Field_Stats[iField];
1232 
1233  if( Statistics.is_Evaluated() )
1234  {
1235  return( true );
1236  }
1237 
1238  if( Get_Max_Samples() > 0 && Get_Max_Samples() < Get_Count() )
1239  {
1240  double d = (double)Get_Count() / (double)Get_Max_Samples();
1241 
1242  for(double i=0; i<(double)Get_Count(); i+=d)
1243  {
1244  CSG_Table_Record *pRecord = m_Records[(sLong)i];
1245 
1246  if( !pRecord->is_NoData(iField) )
1247  {
1248  Statistics += pRecord->asDouble(iField);
1249  }
1250  }
1251 
1252  Statistics.Set_Count(Statistics.Get_Count() >= Get_Max_Samples() ? Get_Count() // any no-data cells ?
1253  : (sLong)(Get_Count() * (double)Statistics.Get_Count() / (double)Get_Max_Samples())
1254  );
1255  }
1256  else
1257  {
1258  for(sLong i=0; i<Get_Count(); i++)
1259  {
1260  CSG_Table_Record *pRecord = m_Records[i];
1261 
1262  if( !pRecord->is_NoData(iField) )
1263  {
1264  Statistics += pRecord->asDouble(iField);
1265  }
1266  }
1267  }
1268 
1269  return( Statistics.Evaluate() ); // evaluate! prevent values to be added more than once!
1270 }
1271 
1272 
1274 // //
1275 // //
1276 // //
1278 
1279 //---------------------------------------------------------
1281 {
1283 
1285 }
1286 
1287 //---------------------------------------------------------
1289 {
1291 
1292  if( m_Index.is_Okay() )
1293  {
1294  _Index_Update();
1295  }
1296 
1297  return( CSG_Data_Object::On_Update() );
1298 }
1299 
1300 
1302 // //
1303 // Index //
1304 // //
1306 
1307 //---------------------------------------------------------
1308 bool CSG_Table::Set_Index(int Field_1, TSG_Table_Index_Order Order_1, int Field_2, TSG_Table_Index_Order Order_2, int Field_3, TSG_Table_Index_Order Order_3)
1309 {
1310  m_Index_Fields.Destroy();
1311 
1312  if( Field_1 >= 0 && Field_1 < m_nFields && Order_1 != TABLE_INDEX_None )
1313  {
1314  Field_1++; m_Index_Fields += Order_1 == TABLE_INDEX_Ascending ? Field_1 : -Field_1;
1315 
1316  if( Field_2 >= 0 && Field_2 < m_nFields && Order_2 != TABLE_INDEX_None )
1317  {
1318  Field_2++; m_Index_Fields += Order_2 == TABLE_INDEX_Ascending ? Field_2 : -Field_2;
1319 
1320  if( Field_3 >= 0 && Field_3 < m_nFields && Order_3 != TABLE_INDEX_None )
1321  {
1322  Field_3++; m_Index_Fields += Order_3 == TABLE_INDEX_Ascending ? Field_3 : -Field_3;
1323  }
1324  }
1325 
1326  _Index_Update();
1327  }
1328  else
1329  {
1330  Del_Index();
1331  }
1332 
1333  return( is_Indexed() );
1334 }
1335 
1336 //---------------------------------------------------------
1338 {
1339  m_Index.Destroy();
1340 
1341  m_Index_Fields.Destroy();
1342 
1343  return( true );
1344 }
1345 
1346 //---------------------------------------------------------
1347 bool CSG_Table::Toggle_Index(int iField)
1348 {
1349  if( iField < 0 || iField >= m_nFields )
1350  {
1351  return( false );
1352  }
1353 
1354  if( iField != Get_Index_Field(0) )
1355  {
1356  return( Set_Index(iField, TABLE_INDEX_Ascending) );
1357  }
1358 
1360  {
1361  return( Set_Index(iField, TABLE_INDEX_Descending) );
1362  }
1363 
1364  return( Del_Index() );
1365 }
1366 
1367 
1369 // //
1371 
1372 //---------------------------------------------------------
1373 class CSG_Table_Record_Compare_Field : public CSG_Index::CSG_Index_Compare
1374 {
1375 public:
1376  CSG_Table_Record_Compare_Field(const CSG_Table *pTable, int Field, bool Ascending)
1377  {
1378  m_pTable = pTable;
1379  m_Field = Field;
1380  m_Ascending = Ascending;
1381 
1382  if( !m_pTable || m_Field < 0 || m_Field >= m_pTable->Get_Field_Count() )
1383  {
1384  m_pTable = NULL;
1385  }
1386  }
1387 
1388  bool is_Okay (void) const { return( m_pTable != NULL ); }
1389 
1390  virtual int Compare (const sLong _a, const sLong _b)
1391  {
1392  sLong a = m_Ascending ? _a : _b;
1393  sLong b = m_Ascending ? _b : _a;
1394 
1395  switch( m_pTable->Get_Field_Type(m_Field) )
1396  {
1397  default: {
1398  double d =
1399  m_pTable->Get_Record(a)->asDouble(m_Field) -
1400  m_pTable->Get_Record(b)->asDouble(m_Field);
1401 
1402  return( d < 0. ? -1 : d > 0. ? 1 : 0 );
1403  }
1404 
1405  case SG_DATATYPE_String:
1406  case SG_DATATYPE_Date :
1407  return( SG_STR_CMP(
1408  m_pTable->Get_Record(a)->asString(m_Field),
1409  m_pTable->Get_Record(b)->asString(m_Field))
1410  );
1411  }
1412  }
1413 
1414 
1415 private:
1416 
1417  bool m_Ascending;
1418 
1419  int m_Field;
1420 
1421  const CSG_Table *m_pTable;
1422 
1423 };
1424 
1425 //---------------------------------------------------------
1426 bool CSG_Table::Set_Index(CSG_Index &Index, int Field, bool bAscending) const
1427 {
1428  CSG_Table_Record_Compare_Field Compare(this, Field, bAscending);
1429 
1430  return( Compare.is_Okay() && Index.Create(Get_Count(), &Compare) );
1431 }
1432 
1433 
1435 // //
1437 
1438 //---------------------------------------------------------
1439 class CSG_Table_Record_Compare_Fields : public CSG_Index::CSG_Index_Compare
1440 {
1441 public:
1442  CSG_Table_Record_Compare_Fields(const CSG_Table *pTable, int Fields[], int nFields, bool Ascending)
1443  : m_pTable(pTable), m_Fields(Fields), m_nFields(nFields)
1444  {
1445  m_Ascending.Create(nFields);
1446 
1447  for(int i=0; m_pTable && i<m_nFields; i++)
1448  {
1449  if( m_Fields[i] >= m_pTable->Get_Field_Count() )
1450  {
1451  m_pTable = NULL;
1452  }
1453 
1454  m_Ascending[i] = Ascending ? 1 : 0;
1455  }
1456  }
1457 
1458  CSG_Table_Record_Compare_Fields(const CSG_Table *pTable, int Fields[], int nFields, int Ascending[])
1459  : m_pTable(pTable), m_Fields(Fields), m_nFields(nFields)
1460  {
1461  m_Ascending.Create(nFields);
1462 
1463  for(int i=0; m_pTable && i<m_nFields; i++)
1464  {
1465  if( m_Fields[i] >= m_pTable->Get_Field_Count() )
1466  {
1467  m_pTable = NULL;
1468  }
1469 
1470  m_Ascending[i] = Ascending[i] > 0 ? 1 : 0;
1471  }
1472  }
1473 
1474  bool is_Okay (void) const { return( m_pTable != NULL ); }
1475 
1476  virtual int Compare (const sLong _a, const sLong _b)
1477  {
1478  int Difference = 0;
1479 
1480  for(int i=0; !Difference && i<m_nFields; i++)
1481  {
1482  int Field = m_Fields[i];
1483 
1484  sLong a = m_Ascending[i] ? _a : _b;
1485  sLong b = m_Ascending[i] ? _b : _a;
1486 
1487  switch( m_pTable->Get_Field_Type(Field) )
1488  {
1489  default: {
1490  double d = m_pTable->Get_Record(a)->asDouble(Field);
1491  d -= m_pTable->Get_Record(b)->asDouble(Field);
1492  Difference = d < 0. ? -1 : d > 0. ? 1 : 0;
1493  } break;
1494 
1495  case SG_DATATYPE_String:
1496  case SG_DATATYPE_Date :
1497  CSG_String s (m_pTable->Get_Record(a)->asString(Field));
1498  Difference = s.Cmp(m_pTable->Get_Record(b)->asString(Field));
1499  break;
1500  }
1501  }
1502 
1503  return( Difference );
1504  }
1505 
1506 
1507 private:
1508 
1509  int *m_Fields, m_nFields;
1510 
1511  CSG_Array_Int m_Ascending;
1512 
1513  const CSG_Table *m_pTable;
1514 
1515 };
1516 
1517 //---------------------------------------------------------
1518 bool CSG_Table::Set_Index(CSG_Index &Index, int Fields[], int nFields, bool bAscending) const
1519 {
1520  CSG_Table_Record_Compare_Fields Compare(this, Fields, nFields, bAscending);
1521 
1522  return( Compare.is_Okay() && Index.Create(Get_Count(), &Compare) );
1523 }
1524 
1525 //---------------------------------------------------------
1526 bool CSG_Table::Set_Index(CSG_Index &Index, const CSG_Array_Int &Fields, bool bAscending) const
1527 {
1528  return( Set_Index(Index, Fields.Get_Array(), (int)Fields.Get_Size(), bAscending) );
1529 }
1530 
1531 //---------------------------------------------------------
1532 void CSG_Table::_Index_Update(void)
1533 {
1534  if( m_Index_Fields.Get_Size() < 1 )
1535  {
1536  Del_Index();
1537  }
1538 
1539  CSG_Array_Int Fields, Ascending;
1540 
1541  for(sLong i=0; i<m_Index_Fields.Get_Size(); i++)
1542  {
1543  Fields += abs(m_Index_Fields[i]) - 1;
1544  Ascending += m_Index_Fields[i] > 0 ? 1 : 0;
1545  }
1546 
1547  CSG_Table_Record_Compare_Fields Compare(this, Fields.Get_Array(), (int)Fields.Get_Size(), Ascending.Get_Array());
1548 
1549  if( !Compare.is_Okay() || !m_Index.Create(Get_Count(), &Compare) )
1550  {
1551  Del_Index();
1552  }
1553 }
1554 
1555 
1557 // //
1558 // //
1559 // //
1561 
1562 //---------------------------------------------------------
CSG_Index
Definition: mat_tools.h:200
CSG_Table::CSG_Table_Record
friend class CSG_Table_Record
Definition: table.h:284
CSG_String::BeforeFirst
CSG_String BeforeFirst(char Character) const
Definition: api_string.cpp:666
CSG_Table::Find_Record
virtual bool Find_Record(sLong &Index, int iField, const CSG_String &Value, bool bCreateIndex=false)
Definition: table.cpp:946
CSG_Table_Record::asDouble
double asDouble(int Field) const
Definition: table_record.cpp:527
CSG_Data_Object::Assign
virtual bool Assign(CSG_Data_Object *pObject)
Definition: dataobject.cpp:793
CSG_Index::is_Okay
bool is_Okay(void) const
Definition: mat_tools.h:238
CSG_Table::Assign
virtual bool Assign(CSG_Data_Object *pTable)
Definition: table.cpp:377
CSG_Data_Object::Get_Max_Samples
sLong Get_Max_Samples(void) const
Definition: dataobject.h:263
SG_FREE_SAFE
#define SG_FREE_SAFE(PTR)
Definition: api_core.h:205
SG_Create_Table
CSG_Table * SG_Create_Table(void)
Definition: table.cpp:65
CSG_Table::Set_Count
virtual bool Set_Count(sLong nRecords)
Definition: table.cpp:926
SG_DATATYPE_String
@ SG_DATATYPE_String
Definition: api_core.h:1005
_TL
#define _TL(s)
Definition: api_core.h:1489
CSG_Table::Del_Records
virtual bool Del_Records(void)
Definition: table.cpp:908
CSG_Array::Get_Size
sLong Get_Size(void) const
Definition: api_core.h:327
CSG_Data_Object::Set_File_Name
void Set_File_Name(const CSG_String &FileName)
Definition: dataobject.cpp:366
CSG_String::Length
size_t Length(void) const
Definition: api_string.cpp:172
TABLE_INDEX_None
@ TABLE_INDEX_None
Definition: table.h:104
CSG_Data_Object::Get_Description
const SG_Char * Get_Description(void) const
Definition: dataobject.cpp:360
CSG_Table_Record
Definition: table.h:130
CSG_Table::_Stats_Update
virtual bool _Stats_Update(int iField) const
Definition: table.cpp:1224
CSG_Data_Object::Get_NoData_Value
double Get_NoData_Value(bool bUpper=false) const
Definition: dataobject.h:253
CSG_Table::Get_ObjectType
virtual TSG_Data_Object_Type Get_ObjectType(void) const
Returns the object type as defined by TSG_Data_Object_Type. Used for run time type checking.
Definition: table.h:316
CSG_Table::Get_Value
virtual bool Get_Value(sLong Index, int iField, CSG_String &Value) const
Definition: table.cpp:1157
SG_UI_MSG_STYLE_SUCCESS
@ SG_UI_MSG_STYLE_SUCCESS
Definition: api_core.h:1505
CSG_Index::CSG_Index_Compare
Definition: mat_tools.h:203
CSG_Table::m_Selection
CSG_Array m_Selection
Definition: table.h:459
CSG_Table::is_Selected
virtual bool is_Selected(sLong Index) const
Definition: table.h:424
CSG_Table::Del_Field
virtual bool Del_Field(int iField)
Definition: table.cpp:520
CSG_Table::Get_Record
virtual CSG_Table_Record * Get_Record(sLong Index) const
Definition: table.h:394
GET_GROW_SIZE
#define GET_GROW_SIZE(n)
Definition: table.cpp:744
CSG_Array_Int::Get_Size
sLong Get_Size(void) const
Definition: api_core.h:436
CSG_Table::m_Field_Name
CSG_String ** m_Field_Name
Definition: table.h:455
CSG_Table::operator=
CSG_Table & operator=(const CSG_Table &Table)
Definition: table.cpp:369
CSG_Table_Record::Assign
virtual bool Assign(CSG_Table_Record *pRecord)
Definition: table_record.cpp:543
CSG_Table::~CSG_Table
virtual ~CSG_Table(void)
Definition: table.cpp:326
CSG_Tool
Definition: tool.h:151
CSG_Index::CSG_Index_Compare::Compare
virtual int Compare(const sLong a, const sLong b)=0
CSG_Table::Destroy
virtual bool Destroy(void)
Definition: table.cpp:332
CSG_Data_Object::Get_Name
const SG_Char * Get_Name(void) const
Definition: dataobject.cpp:349
CSG_Tool::Execute
bool Execute(bool bAddHistory=false)
Definition: tool.cpp:258
SG_FILE_ENCODING_UTF32BE
@ SG_FILE_ENCODING_UTF32BE
Definition: api_core.h:556
CSG_Table::CSG_Table
CSG_Table(void)
Definition: table.cpp:133
CSG_Table::Get_Index_Order
TSG_Table_Index_Order Get_Index_Order(int i) const
Definition: table.h:442
CSG_Table::Get_Field_Count
int Get_Field_Count(void) const
Definition: table.h:356
CSG_Array_Int::Get_Array
int * Get_Array(void) const
Definition: api_core.h:439
CSG_Simple_Statistics::Evaluate
bool Evaluate(void)
Definition: mat_tools.cpp:473
SG_Free
SAGA_API_DLL_EXPORT void SG_Free(void *memblock)
Definition: api_memory.cpp:83
SG_STR_CMP
#define SG_STR_CMP(s1, s2)
Definition: api_core.h:544
CSG_Table::Get_Field_Length
int Get_Field_Length(int iField, int Encoding=SG_FILE_ENCODING_UNDEFINED) const
Definition: table.cpp:659
CSG_Table_Record::m_Values
class CSG_Table_Value ** m_Values
Definition: table.h:256
CSG_Table::Set_Record
virtual bool Set_Record(sLong Index, CSG_Table_Record *pCopy)
Definition: table.cpp:858
CSG_Table_Value
Definition: table_value.h:111
CSG_Table_Record::m_Index
sLong m_Index
Definition: table.h:254
CSG_Tool_Library_Manager::Delete_Tool
bool Delete_Tool(CSG_Tool *pTool) const
Definition: tool_library.cpp:725
CSG_Data_Object::Set_Update_Flag
void Set_Update_Flag(bool bOn=true)
Definition: dataobject.h:285
CSG_Table_Record::is_NoData
bool is_NoData(int Field) const
Definition: table_record.cpp:416
CSG_Table::Set_Modified
virtual void Set_Modified(bool bModified=true)
Definition: table.cpp:1113
CSG_String::Cmp
int Cmp(const CSG_String &String) const
Definition: api_string.cpp:515
SG_FILE_ENCODING_UTF7
@ SG_FILE_ENCODING_UTF7
Definition: api_core.h:551
CSG_Table::_Stats_Invalidate
bool _Stats_Invalidate(void) const
Definition: table.cpp:1200
CSG_Table::m_Field_Type
TSG_Data_Type * m_Field_Type
Definition: table.h:453
CSG_Table::Find_Field
int Find_Field(const CSG_String &Name) const
Definition: table.cpp:713
SG_UI_MSG_STYLE_FAILURE
@ SG_UI_MSG_STYLE_FAILURE
Definition: api_core.h:1506
CSG_Table::is_Compatible
bool is_Compatible(const CSG_Table &Table, bool bExactMatch=false) const
Definition: table.cpp:430
SG_File_Exists
SAGA_API_DLL_EXPORT bool SG_File_Exists(const CSG_String &FileName)
Definition: api_file.cpp:850
SG_TOOL_PARAMETER_SET
#define SG_TOOL_PARAMETER_SET(IDENTIFIER, VALUE)
Definition: tool_library.h:351
CSG_Table::m_Field_Stats
CSG_Simple_Statistics ** m_Field_Stats
Definition: table.h:457
CSG_Table_Record::asString
const SG_Char * asString(int Field, int Decimals=-99) const
Definition: table_record.cpp:461
CSG_Data_Object
Definition: dataobject.h:180
CSG_Data_Object::On_NoData_Changed
virtual bool On_NoData_Changed(void)
Definition: dataobject.cpp:601
CSG_Table::Get_Field_Name
const SG_Char * Get_Field_Name(int iField) const
Definition: table.h:357
CSG_Simple_Statistics::Get_Count
sLong Get_Count(void) const
Definition: mat_tools.h:743
CSG_Table::Get_Selection_Count
sLong Get_Selection_Count(void) const
Definition: table.h:420
CSG_Index::Create
bool Create(sLong nValues, CSG_Index_Compare &Compare)
Definition: mat_indexing.cpp:110
CSG_Tool_Library_Manager::Create_Tool
CSG_Tool * Create_Tool(const CSG_String &Library, int Index, bool bWithGUI=false) const
Definition: tool_library.cpp:696
TSG_Table_Index_Order
TSG_Table_Index_Order
Definition: table.h:103
sLong
signed long long sLong
Definition: api_core.h:158
SG_Get_Tool_Library_Manager
CSG_Tool_Library_Manager & SG_Get_Tool_Library_Manager(void)
Definition: tool_library.cpp:286
CSG_Data_Object::On_Update
virtual bool On_Update(void)
Definition: dataobject.h:287
CSG_Table::is_Indexed
bool is_Indexed(void) const
Definition: table.h:437
CSG_Table::On_NoData_Changed
virtual bool On_NoData_Changed(void)
Definition: table.cpp:1280
SG_FILE_ENCODING_UTF32LE
@ SG_FILE_ENCODING_UTF32LE
Definition: api_core.h:555
CSG_Table::Mov_Field
virtual bool Mov_Field(int iField, int Position)
Definition: table.cpp:558
CSG_Table::Get_Count
sLong Get_Count(void) const
Definition: table.h:392
CSG_Table_Record::_Create_Value
static CSG_Table_Value * _Create_Value(TSG_Data_Type Type)
Definition: table_record.cpp:110
CSG_Table::On_Update
virtual bool On_Update(void)
Definition: table.cpp:1288
CSG_Data_Object::is_Modified
virtual bool is_Modified(void) const
Definition: dataobject.h:228
CSG_Simple_Statistics::Invalidate
void Invalidate(void)
Definition: mat_tools.cpp:447
CSG_Table::Assign_Values
bool Assign_Values(const CSG_Table &Table)
Definition: table.cpp:395
CSG_Array_Int
Definition: api_core.h:423
CSG_Simple_Statistics::is_Evaluated
int is_Evaluated(void) const
Definition: mat_tools.h:739
CSG_Table::Get_Index_Field
int Get_Index_Field(int i) const
Definition: table.h:441
CSG_Table::Del_Index
bool Del_Index(void)
Definition: table.cpp:1337
CSG_Table::m_nBuffer
sLong m_nBuffer
Definition: table.h:451
CSG_Data_Object::Set_Modified
virtual void Set_Modified(bool bOn=true)
Definition: dataobject.h:227
CSG_Array::Create
void * Create(const CSG_Array &Array)
Definition: api_memory.cpp:250
CSG_Table::Set_Value
virtual bool Set_Value(sLong Index, int iField, const SG_Char *Value)
Definition: table.cpp:1131
CSG_Array::Get_Array
void * Get_Array(void) const
Definition: api_core.h:336
CSG_Table::Get_Record_byIndex
CSG_Table_Record * Get_Record_byIndex(sLong Index) const
Definition: table.h:399
CSG_Data_Object::asTable
class CSG_Table * asTable(bool bPolymorph=false) const
Definition: dataobject.cpp:487
SG_DATATYPE_Date
@ SG_DATATYPE_Date
Definition: api_core.h:1006
CSG_Table_Record::_Add_Field
bool _Add_Field(int add_Field)
Definition: table_record.cpp:143
CSG_Data_Object::Set_Name
void Set_Name(const CSG_String &Name)
Definition: dataobject.cpp:300
CSG_Table::m_Encoding
int m_Encoding
Definition: table.h:449
CSG_Table_Record::Set_Modified
void Set_Modified(bool bOn=true)
Definition: table_record.cpp:220
CSG_Index::Add_Entry
bool Add_Entry(sLong Position=-1)
Definition: mat_indexing.cpp:268
CSG_Simple_Statistics::Set_Count
bool Set_Count(sLong Count)
Definition: mat_tools.cpp:424
CSG_String::Format
static CSG_String Format(const char *Format,...)
Definition: api_string.cpp:270
CSG_Table::_Del_Selection
bool _Del_Selection(sLong Index)
Definition: table_selection.cpp:87
SG_FILE_ENCODING_UTF16LE
@ SG_FILE_ENCODING_UTF16LE
Definition: api_core.h:553
CSG_Table::Set_Field_Name
bool Set_Field_Name(int iField, const SG_Char *Name)
Definition: table.cpp:611
CSG_Table::Add_Field
virtual bool Add_Field(const CSG_String &Name, TSG_Data_Type Type, int Position=-1)
Definition: table.cpp:481
CSG_Table
Definition: table.h:283
CSG_String::to_UTF8
size_t to_UTF8(char **pString) const
Definition: api_string.cpp:813
SG_DATAOBJECT_TYPE_Shapes
@ SG_DATAOBJECT_TYPE_Shapes
Definition: dataobject.h:121
TABLE_INDEX_Descending
@ TABLE_INDEX_Descending
Definition: table.h:106
CSG_String::AfterFirst
CSG_String AfterFirst(char Character) const
Definition: api_string.cpp:644
CSG_Table::Del_Record
virtual bool Del_Record(sLong Index)
Definition: table.cpp:869
SG_Char
#define SG_Char
Definition: api_core.h:536
CSG_Table::Load
bool Load(const CSG_String &File, int Format, SG_Char Separator, int Encoding=SG_FILE_ENCODING_UNDEFINED)
Definition: table_io.cpp:99
shapes.h
CSG_String
Definition: api_core.h:563
CSG_Tool::Set_Manager
bool Set_Manager(class CSG_Data_Manager *pManager)
Definition: tool.cpp:570
SG_DATAOBJECT_TYPE_Table
@ SG_DATAOBJECT_TYPE_Table
Definition: dataobject.h:120
CSG_Data_Object::Set_Description
void Set_Description(const CSG_String &Description)
Definition: dataobject.cpp:355
CSG_String::is_Empty
bool is_Empty(void) const
Definition: api_string.cpp:178
SG_FILE_ENCODING_UTF16BE
@ SG_FILE_ENCODING_UTF16BE
Definition: api_core.h:554
TSG_Table_File_Type
TSG_Table_File_Type
Definition: table.h:93
CSG_Table_Record::Set_Value
bool Set_Value(int Field, const CSG_String &Value)
Definition: table_record.cpp:270
CSG_Table::m_nFields
int m_nFields
Definition: table.h:449
GET_RECORD
#define GET_RECORD(i)
CSG_Table::Ins_Record
virtual CSG_Table_Record * Ins_Record(sLong Index, CSG_Table_Record *pCopy=NULL)
Definition: table.cpp:801
CSG_Table_Record::Get_Index
sLong Get_Index(void) const
Definition: table.h:136
TABLE_INDEX_Ascending
@ TABLE_INDEX_Ascending
Definition: table.h:105
CSG_Table::Create
bool Create(void)
Definition: table.cpp:139
CSG_Tool::On_Before_Execution
virtual bool On_Before_Execution(void)
Definition: tool.h:244
CSG_Shapes
Definition: shapes.h:775
SG_UI_ProgressAndMsg_Lock
void SG_UI_ProgressAndMsg_Lock(bool bOn)
Definition: api_callback.cpp:590
CSG_String::c_str
const SG_Char * c_str(void) const
Definition: api_string.cpp:236
tool_library.h
CSG_Table_Record::Get_Value
CSG_Table_Value * Get_Value(int Field)
Definition: table.h:237
TSG_Data_Type
TSG_Data_Type
Definition: api_core.h:993
SG_Realloc
SAGA_API_DLL_EXPORT void * SG_Realloc(void *memblock, size_t size)
Definition: api_memory.cpp:77
CSG_Table::Set_Index
bool Set_Index(CSG_Index &Index, int Field, bool bAscending=true) const
Definition: table.cpp:1426
CSG_Table::Get_Field_Type
TSG_Data_Type Get_Field_Type(int iField) const
Definition: table.h:358
CSG_Table::Add_Record
virtual CSG_Table_Record * Add_Record(CSG_Table_Record *pCopy=NULL)
Definition: table.cpp:795
CSG_Index::Del_Entry
bool Del_Entry(sLong Position=-1)
Definition: mat_indexing.cpp:289
CSG_Table::Get_Field
int Get_Field(const CSG_String &Name) const
Definition: table.cpp:695
CSG_Array_Int::Destroy
void Destroy(void)
Definition: api_core.h:431
SG_FILE_ENCODING_UTF8
@ SG_FILE_ENCODING_UTF8
Definition: api_core.h:552
CSG_Simple_Statistics
Definition: mat_tools.h:723
CSG_Data_Object::Set_NoData_Value_Range
virtual bool Set_NoData_Value_Range(double Lower, double Upper)
Definition: dataobject.cpp:578
CSG_Table::Set_Field_Type
virtual bool Set_Field_Type(int iField, TSG_Data_Type Type)
Definition: table.cpp:626
table.h
CSG_Index::Destroy
bool Destroy(void)
Definition: mat_indexing.cpp:83
CSG_Data_Object::Destroy
virtual bool Destroy(void)
Definition: dataobject.cpp:281
CSG_Table::Toggle_Index
bool Toggle_Index(int iField)
Definition: table.cpp:1347
CSG_Table::_Get_New_Record
virtual CSG_Table_Record * _Get_New_Record(sLong Index)
Definition: table.cpp:789
SG_DATAOBJECT_TYPE_PointCloud
@ SG_DATAOBJECT_TYPE_PointCloud
Definition: dataobject.h:123
CSG_Table::m_nRecords
sLong m_nRecords
Definition: table.h:451
SG_UI_Msg_Add
void SG_UI_Msg_Add(const char *Message, bool bNewLine, TSG_UI_MSG_STYLE Style)
Definition: api_callback.cpp:503
CSG_Table_Record::_Del_Field
bool _Del_Field(int del_Field)
Definition: table_record.cpp:167
CSG_Table::_On_Construction
virtual void _On_Construction(void)
Definition: table.cpp:302
SG_Create_Shapes
CSG_Shapes * SG_Create_Shapes(void)
Definition: shapes.cpp:85