Giant database dbf

This forum is for eXpress++ general support.
Message
Author
User avatar
Eugene Lutsenko
Posts: 1649
Joined: Sat Feb 04, 2012 2:23 am
Location: Russia, Southern federal district, city of Krasnodar
Contact:

Re: Giant database dbf

#21 Post by Eugene Lutsenko »

I found documentation in Russian language for the use of ADS in Alaska. Read. Something somehow does not inspire. All the time begins with the connection to the ADS server. It turns out that it must be installed and running on your computer. And local use without starting the server with the standard means of Alaska never found.
Attachments
Безымянный.jpg
Безымянный.jpg (163.7 KiB) Viewed 13044 times

User avatar
rdonnay
Site Admin
Posts: 4729
Joined: Wed Jan 27, 2010 6:58 pm
Location: Boise, Idaho USA
Contact:

Re: Giant database dbf

#22 Post by rdonnay »

It turns out that it must be installed and running on your computer.
I will write you a small program to show you how to get started.
What is the name of your database?
The eXpress train is coming - and it has more cars.

User avatar
Eugene Lutsenko
Posts: 1649
Joined: Sat Feb 04, 2012 2:23 am
Location: Russia, Southern federal district, city of Krasnodar
Contact:

Re: Giant database dbf

#23 Post by Eugene Lutsenko »

rdonnay wrote:
It turns out that it must be installed and running on your computer.
I will write you a small program to show you how to get started.
What is the name of your database?
Thank you very much, Roger!

You all understand very well that every beginning is difficult. Then I hope it will be easier. I think the good name of the database will start.dbt. It would be very nice if you could set the values of variables in prg-file the number of fields and number of records in the database. I already anticipate that it will be possible to create a database with number fields up to 30,000 with the number of records that the database will have a size of 100 GB.

User avatar
rdonnay
Site Admin
Posts: 4729
Joined: Wed Jan 27, 2010 6:58 pm
Location: Boise, Idaho USA
Contact:

Re: Giant database dbf

#24 Post by rdonnay »

If you anticipate 30,000 fields and 100gb then I don't think that a DBF will work for you even with Ads.

I tried to create a database with 30,000 fields and I got an IDSC error.
The eXpress train is coming - and it has more cars.

User avatar
Eugene Lutsenko
Posts: 1649
Joined: Sat Feb 04, 2012 2:23 am
Location: Russia, Southern federal district, city of Krasnodar
Contact:

Re: Giant database dbf

#25 Post by Eugene Lutsenko »

What in bases the dbt can be up to 30,000 fields - I read about the ADS:
http://devzone.advantagedatabase.com/dz ... index.html
http://www.delphisite.ru/faq/advantage-database-server

The maximum number of fields in a table depends on the long name field , and can be calculated: 65135 / ( 10 + AverageFieldNameLength ). For example, if average length of field names is 10, the maximum number of fields - 3256

If it is possible to use a database larger than 2GB, then it will be valuable (they write: with NTFS 16 exabytes (18,446,744,073,709,551,616 bytes))

In my experience the limit on the database size plays a big role, which is the number of fields. The number of fields is usually enough, but with the size of the database the problem occurs more often. If you remove this problem, it will be very important and will be very valuable.

User avatar
Eugene Lutsenko
Posts: 1649
Joined: Sat Feb 04, 2012 2:23 am
Location: Russia, Southern federal district, city of Krasnodar
Contact:

Re: Giant database dbf

#26 Post by Eugene Lutsenko »

rdonnay wrote:If you anticipate 30,000 fields and 100gb then I don't think that a DBF will work for you even with Ads.

I tried to create a database with 30,000 fields and I got an IDSC error.
I made a few functions that allow me to do database any dimension and number of fields and number of records. I conducted numerical experiments with a database of 100,000 fields and 100,000 records.

This database size of approximately 240 GB and was created about half an hour. I compared these text base size of a DBF. It turned out they were almost the same size with the same dimensions.

Code: Select all

********************************************
******** Запись поля в Max_БД
********************************************
FUNCTION LC_FieldPut( DB_name, nHandle, mRec, mCol, String )

Pos = (mRec-1) * Len_LcBuf + aPos[mCol] - 1

FSEEK(nHandle, Pos, FS_SET)     // Позиционирование начала поля
Len_str = LEN(String)
N_Write = FWrite( nHandle, String, Len_str )

IF N_Write < Len_str
   aMess := {}
   AADD(aMess, 'Ошибка записи поля: [строка=@, колонка=$] БД: "#".')
   AADD(aMess, '')
   AADD(aMess, 'Это неустранимая ошибка, возникающая при попытке открытия уже открытой базы данных модели: '+DB_Name+'.')
   AADD(aMess, 'Скорее всего она возникла из-за того, что перед запуском нового режима не был закрыт предыдущий.')
   AADD(aMess, 'Работа системы будет прервана. Если после этого сразу запустить режим, в котором возникла ошибка,')
   AADD(aMess, 'то скорее всего он будет выполнен нормально.')
   aMess[1] = STRTRAN(aMess[1], "#", DB_Name)
   aMess[1] = STRTRAN(aMess[1], "@", ALLTRIM(STR(mRec)))
   aMess[1] = STRTRAN(aMess[1], "$", ALLTRIM(STR(mCol)))
   LB_Warning(aMess)
*  MsgBox(aMess)
   QUIT
   RETURN(.T.)
ENDIF

RETURN(.F.)

********************************************
******** Считывание поля из Max_БД
********************************************
FUNCTION LC_FieldGet( DB_name, nHandle, mRec, mCol )

*MsgBox('Строка='+ALLTRIM(STR(mRec))+', Колонка='+ALLTRIM(STR(mCol)))

Len_str = aInfStruct[mCol,3]

Pos = (mRec-1) * Len_LcBuf + aPos[mCol] - 1

FSEEK(nHandle, Pos, FS_SET)     // Позиционирование начала поля
String = SPACE(Len_str)
N_Read = FRead( nHandle, @String, Len_str )

IF N_Read < Len_str
   aMess := {}
   AADD(aMess, 'Ошибка считывания поля: [строка=@, колонка=$] БД: "#".')
   AADD(aMess, '')
   AADD(aMess, 'Это неустранимая ошибка, возникающая при попытке открытия уже открытой базы данных модели: '+DB_Name+'.')
   AADD(aMess, 'Скорее всего она возникла из-за того, что перед запуском нового режима не был закрыт предыдущий.')
   AADD(aMess, 'Работа системы будет прервана. Если после этого сразу запустить режим, в котором возникла ошибка,')
   AADD(aMess, 'то скорее всего он будет выполнен нормально.')
   aMess[1] = STRTRAN(aMess[1], "#", DB_Name)
   aMess[1] = STRTRAN(aMess[1], "@", ALLTRIM(STR(mRec)))
   aMess[1] = STRTRAN(aMess[1], "$", ALLTRIM(STR(mCol)))
   LB_Warning(aMess)
*  MsgBox(aMess)
   QUIT
   RETURN("")
ENDIF

// Пробел в числовом поле рассматривается как "0"
IF aInfStruct[mCol,2] = "N" .AND. LEN(ALLTRIM(String)) = 0    
   String = "0"
ENDIF

RETURN(String)
[/size]

Examples of calls to these functions:

Code: Select all

   // Суммирование 1 в ячейки БД Abs.dbf, соответствующие строкам и столбцам,
   // а также в строку и столбец "Сумма" и строку: Кол-во объектов по классам"

   IF LEN(Ar_Kcl) > 0 .AND. LEN(Ar_Kpr) > 0
      FOR i=1 TO LEN(Ar_Kpr)
          For j=1 TO LEN(Ar_Kcl)
              String   = LC_FieldGet( Ar_Model[1]+".txt", nHandle[1], Ar_Kpr[i], 2+Ar_Kcl[j] )          // Считывание поля из БД (корректная) #######
              String   = STR(VAL(String)+1, aInfStruct[2+Ar_Kcl[j],3],aInfStruct[2+Ar_Kcl[j],4] )       // Ячейка [i,j]++
              Flag_err = LC_FieldPut( Ar_Model[1]+".txt", nHandle[1], Ar_Kpr[i], 2+Ar_Kcl[j], String )  // Запись поля в БД (корректная) ############
              Ar_Summ_j[Ar_Kcl[j]] = Ar_Summ_j[Ar_Kcl[j]] + 1         // Строка  "Сумма абс.частот" по столбцам
              Ar_Summ_i[Ar_Kpr[i]] = Ar_Summ_i[Ar_Kpr[i]] + 1         // Столбец "Сумма абс.частот" по строкам
              Summa_Nij++                                             // Сумма Nij по всей БД Abs.txt
              aColEmpty[Ar_Kcl[j]] = .T.                              // .T., если колонка не пустая и .F. - если пустая
              aStrEmpty[Ar_Kpr[i]] = .T.                              // .T., если строка  не пустая и .F. - если пустая
          NEXT
      NEXT
[/size]

The opening of all text databases:

Code: Select all

* ###########################################################################
// Открытие текстовых баз данных ********************************************
// Определить максимальную длину наименования: ОПИСАТЕЛЬНАЯ ШКАЛА-градация
mLenNameMax = 33
FOR i=1 TO N_Gos
    SELECT Gr_OpSc;DBGOTO(i)
    M_NameGrOS = ALLTRIM(Name_GrOS)
    M_KodOpSc  = Kod_OpSc
    SELECT Opis_Sc;DBGOTO(M_KodOpSc)
    M_NameOS = UPPER(ALLTRIM(Name_OpSc))
    // Если в названии градации уже включено наим.шкалы, то повторно не включать его
    IF AT(M_NameOS, UPPER(M_NameGrOS)) = 0
       M_Name = M_NameOS+"-"+M_NameGrOS
    ELSE
       M_Name = M_NameGrOS
    ENDIF
    mLenNameMax = MAX(mLenNameMax, LEN(M_Name))
NEXT

*DC_ASave(aInfStruct, "_InfStruct.arx")      // Когда БД создается - записывать структуру, когда открывается - считывать
aInfStruct = DC_ARestore("_InfStruct.arx")

*DC_ASave(aStrEmpty, "_aStrEmpty.arx")       // Записывать только после расчета Abs.txt, а при расчете остальных БД только считывать
*DC_ASave(aColEmpty, "_aColEmpty.arx")
aStrEmpty = DC_ARestore("_aStrEmpty.arx")
aColEmpty = DC_ARestore("_aColEmpty.arx")

*************************************************

***** Формирование пустой записи
N_Col  = N_Cls+5             // Число полей
CrLf   = CHR(13)+CHR(10)     // Конец строки (записи)
Lc_buf = ""
FOR j=1 TO N_Col
*   S = IF(j=2*INT(j/2),"#","X")        // Для отладки
    S = " "                             // Для работы
    Lc_buf = Lc_buf + REPLICATE(S, aInfStruct[j,3])
NEXT
Lc_buf = Lc_buf + CrLf
Len_LcBuf = LEN(Lc_buf)

****** Создаем стат.базы и базы знаний (7 по частным критериям знаний)
PUBLIC Ar_Model := {"Abs","Prc1","Prc2","Inf1","Inf2","Inf3","Inf4","Inf5","Inf6","Inf7" }
PUBLIC nHandle[LEN(Ar_Model)]

FOR z=1 TO LEN(Ar_Model)
    nHandle[z] := FOpen( Ar_Model[z]+".txt", FO_READWRITE )   // Открыть все текстовые базы данных ########################################
NEXT

**** Рассчет массива начальных позиций полей в строке
PRIVATE aPos[N_Col]
aPos[1] = 1
FOR j=2 TO N_Col
    aPos[j] = aPos[j-1] + aInfStruct[j-1,3]
NEXT
* ###########################################################################
[/size]

Create an array of structures aInfStruct text database:

Code: Select all

* ###########################################################################
// Определить максимальную длину наименования: ОПИСАТЕЛЬНАЯ ШКАЛА-градация
mLenNameMax = 33
FOR i=1 TO N_Gos
    SELECT Gr_OpSc;DBGOTO(i)
    M_NameGrOS = ALLTRIM(Name_GrOS)
    M_KodOpSc  = Kod_OpSc
    SELECT Opis_Sc;DBGOTO(M_KodOpSc)
    M_NameOS = UPPER(ALLTRIM(Name_OpSc))
    // Если в названии градации уже включено наим.шкалы, то повторно не включать его
    IF AT(M_NameOS, UPPER(M_NameGrOS)) = 0
       M_Name = M_NameOS+"-"+M_NameGrOS
    ELSE
       M_Name = M_NameGrOS
    ENDIF
    mLenNameMax = MAX(mLenNameMax, LEN(M_Name))
NEXT

********** Структура создаваемой базы ***********

aInfStruct := { { "Kod_pr", "N",         15, 0},;   // 1
                { "Name"  , "C",mLenNameMax, 0} }   // 2
FOR j=1 TO N_Cls
    FieldName = "N"+ALLTRIM(STR(j,15))
    AADD(aInfStruct, { FieldName, "N", 19, 1 })
NEXT
AADD(aInfStruct, { "Summa", "N", 19, 0 })
AADD(aInfStruct, { "Sredn", "N", 19, 7 })
AADD(aInfStruct, { "Disp" , "N", 19, 7 })

DC_ASave(aInfStruct, "_AbsStruct.arx")      // Когда БД создается - записывать структуру, когда открывается - считывать
*aInfStruct = DC_ARestore("_AbsStruct.arx")

*************************************************

DB_name = "Abs.txt"
nHandle := FCreate( DB_name, FC_NORMAL )                   // Создание БД (если она была, то все равно создается пустая)

IF nHandle = -1
   MsgBox("Файл: "+DB_name+" не может быть создан. Ошибка:"+FERROR())
   RETURN NIL
ENDIF

***** Формирование пустой записи
N_Col  = N_Cls+5             // Число полей
CrLf   = CHR(13)+CHR(10)     // Конец строки (записи)
Lc_buf = ""
FOR j=1 TO N_Col
*   S = IF(j=2*INT(j/2),"#","X")        // Для отладки
    S = " "                             // Для работы
    Lc_buf = Lc_buf + REPLICATE(S, aInfStruct[j,3])
NEXT
Lc_buf = Lc_buf + CrLf
Len_LcBuf = LEN(Lc_buf)

LC_DbCreate( DB_name, nHandle, Lc_buf, N_Gos+4 )           // Создание БД.txt, содержащей N_Rec пустых записей ############
*nHandle := FOpen( DB_name, FO_READWRITE )                 // Открытие базы данных ############################################

**** Расчет массива начальных позиций полей в строке
PRIVATE aPos[N_Col]
aPos[1] = 1
FOR j=2 TO N_Col
    aPos[j] = aPos[j-1] + aInfStruct[j-1,3]
NEXT

* ###########################################################################
[/size]

Of course, this is not a complete database, because I haven't done them in adding and deleting records, etc., but in this case I do not need it. And to use it at all much less convenient than standard databases. So I'm interested in ADS.

http://jobtools.ru/dbfshow/#comment-695
Attachments
1.zip
(873.7 KiB) Downloaded 673 times

User avatar
rdonnay
Site Admin
Posts: 4729
Joined: Wed Jan 27, 2010 6:58 pm
Location: Boise, Idaho USA
Contact:

Re: Giant database dbf

#27 Post by rdonnay »

I don't understand. If you say you can create a 260gb database with 100,000 fields, then why do you need ADS? What DBE are you using to create this database?
The eXpress train is coming - and it has more cars.

User avatar
Eugene Lutsenko
Posts: 1649
Joined: Sat Feb 04, 2012 2:23 am
Location: Russia, Southern federal district, city of Krasnodar
Contact:

Re: Giant database dbf

#28 Post by Eugene Lutsenko »

rdonnay wrote:I don't understand. If you say you can create a 260gb database with 100,000 fields, then why do you need ADS? What DBE are you using to create this database?
I used not quite a database, just text file. But I made an array structure, which directly calculates the position of the fields in this. txt file. And the field size is known from the structure. The structure I write down in a file And simply read or write the field values to positions in a. txt file. '_InfStruct.arx'. All is working well. But the rest of the functions for work with databases I missed. For example, did not implement the functionality of adding records and deleting. This method is less convenient than the standard databases. Use it every time is inconvenient. I use it only for matrix models, which can be very large dimension. For example now I work on creating and testing the reliability of 10 models in which more than 40,000 fields. Used this method. But the system some times crashes, because other databases became larger than 2GB. This was due to the very large number of respondents in the study sample: more than 20,000 people. So I thought, what could be more convenient to use for such cases ADS. And now I just before adding the records in the database checking their size (or rather the number of records and record size I know). If the database size approaches the 2GB I just removed from it less meaningful results. And all the results are written to text output forms.

I had the idea that You could have done all incomparably better than I can. For this we need to keep the very structure of the database file of the most database. The structure can be of any size. Just have to be a sign of the end of the structure. Continue to do everything as I have. Realize all the functions. It is possible to use archiving and unzipping on the fly to significantly reduce the size of the databases. Realize all the functions. To do something like DBE (CLIPPER) or DOT (ALASKA).

In the attached file example databases of low dimensionality in textual form that has no restrictions, in the conventional DBF.

Also is the program that I didn't write that allows you to create a DBF with any number of fields. This is done by physically adjusting the header of DBF-file with direct access. But there is a 64K limit on the total length has a complete or field sizes in the record.

Я использовал не вполне базы данных, а просто текстовый файл. Но я сделал массив структуры, по которому вычисляю прямо позицию поля в этом txt-файле. А размер поля известен из структуры. Структуру я записываю в виде файла: И просто считываю или записываю значения полей по позициям в txt-файле. '_InfStruct.arx'. Все работает хорошо. Но остальных функций по работе с базами данных я не реализовал. Например не реализовал функцию добавления записи и удаления. Этот способ работы менее удобен, чем со стандартными базами данных. Использовать его каждый раз неудобно. Я это использую только для работы с матрицами моделей, которые могут быть очень большой размерности. Например сейчас у меня на работе идет создание и проверка на достоверность 10 моделей, в которых более 40000 полей. Используется именно этот способ. Но система несколько раз вылетала, т.к. другие базы данных становились больше 2Гб. Это происходило из-за очень большого числа респондентов в исследуемой выборке: более 20000 человек. Вот я и подумал, что может быть удобнее будет использовать для подобных случаев ADS. А сейчас я просто перед добавлением записи в базы данных проверяю их размер (точнее число записей, а размер записи я знаю). Если размер базы приближается к 2Гб я просто удаляю из нее менее значимые результаты. А все результаты записываю в текстовые выходные формы.

У меня была мысль, что Вы могли бы сделать все несопоставимо лучше, чем я. Для этого надо хранить саму структуру базы в файле самой этой базы. При этом структура может быть любого размера. Просто должен быть признак ее окончания в файле. Дальше все делать как у меня. Реализовать все функции. Возможно применить архивирование и разархивирование на лету для существенного сокращения размера баз данных. Реализовать все функции. Сделать что-то вроде DBE (CLIPPER) или DOT (ALASKA)

В прикрепленном файле пример баз данных малой размерности в текстовой форме, которая не имеет никаких ограничений, и в обычном DBF.

Также приводится программа, которую не я писал, которая позволяет создавать DBF с любым числом полей. Это сделано путем физической корректировки заголовка DBF-файла при прямом доступе к нему. Но при этом есть ограничение 64К на суммарную длину имеет полней или размеров полей в записи.


The whole system with source code here:
http://lc.kubagro.ru/aidos/_Aidos-X.htm
Attachments
Downloads.rar
(255.09 KiB) Downloaded 656 times
Last edited by Eugene Lutsenko on Sun Feb 26, 2017 10:43 am, edited 1 time in total.

User avatar
rdonnay
Site Admin
Posts: 4729
Joined: Wed Jan 27, 2010 6:58 pm
Location: Boise, Idaho USA
Contact:

Re: Giant database dbf

#29 Post by rdonnay »

I think that you will probably need to create your own database design for your project. DBF format just will not work for you. I know of no DBE for Xbase++ that can handle your requirements.
The eXpress train is coming - and it has more cars.

User avatar
Eugene Lutsenko
Posts: 1649
Joined: Sat Feb 04, 2012 2:23 am
Location: Russia, Southern federal district, city of Krasnodar
Contact:

Re: Giant database dbf

#30 Post by Eugene Lutsenko »

rdonnay wrote:I think that you will probably need to create your own database design for your project. DBF format just will not work for you. I know of no DBE for Xbase++ that can handle your requirements.
I understand, and therefore did so. But in some cases, ADS would be enough and it is better than DBF. And what You have to offer, I would be able to do if I was doing just that. But I need it only for development system. And this development is my initiative. I don't have to do it on their official duties. Do not pay for it. But I need it for the management of the educational process and scientific research in this form, as imagine.

In the link txt-base large dimensions: more than 40,000 fields
http://lc.kubagro.ru/Inf1.zip

Post Reply