35.6. Библиотека pgtypes
Библиотека pgtypes сопоставляет типы базы данных PostgreSQL с их эквивалентами в C, которые можно использовать в программах на C. Она также предлагает функции для выполнения простых вычислений с этими типами в C, то есть без помощи сервера PostgreSQL. Рассмотрите следующий пример:
EXEC SQL BEGIN DECLARE SECTION;
   date date1;
   timestamp ts1, tsout;
   interval iv1;
   char *out;
EXEC SQL END DECLARE SECTION;
PGTYPESdate_today(&date1);
EXEC SQL SELECT started, duration INTO :ts1, :iv1 FROM datetbl WHERE d=:date1;
PGTYPEStimestamp_add_interval(&ts1, &iv1, &tsout);
out = PGTYPEStimestamp_to_asc(&tsout);
printf("Started + duration: %s\n", out);
PGTYPESchar_free(out);
35.6.1. Символьные строки
Некоторые функции, в частности PGTYPESnumeric_to_asc, возвращают указатель на строку в выделенной для неё памяти. Их результаты должны освобождаться функцией PGTYPESchar_free, а не free. (Это важно только в Windows, где выделение и освобождение памяти в определённых случаях должно производиться одной библиотекой.)
35.6.2. Тип numeric
Тип numeric позволяет производить вычисления с произвольной точностью. Эквивалентный ему тип на сервере PostgreSQL описан в Разделе 8.1. Ввиду того, что переменная имеет произвольную точность, она должна расширяться и сжиматься динамически. Поэтому такие переменные можно создавать только в области кучи, используя функции PGTYPESnumeric_new и PGTYPESnumeric_free. Тип decimal подобен numeric, но имеет ограниченную точность, и поэтому может размещаться и в области кучи, и в стеке.
Для работы с типом numeric можно использовать следующие функции:
- PGTYPESnumeric_new
- Запрашивает указатель на новую переменную, размещённую в памяти. - numeric *PGTYPESnumeric_new(void); 
- PGTYPESnumeric_free
- Освобождает переменную типа numeric, высвобождая всю её память. - void PGTYPESnumeric_free(numeric *var); 
- PGTYPESnumeric_from_asc
- Разбирает числовой тип из строковой записи. - numeric *PGTYPESnumeric_from_asc(char *str, char **endptr); - Допускаются в частности следующие форматы: - -2,- .794,- +3.44,- 592.49E07и- -32.84e-4. Если значение удаётся разобрать успешно, возвращается действительный указатель, в противном случае указатель NULL. На данный момент ECPG всегда разбирает строку до конца, так что эта функция не может вернуть адрес первого недопустимого символа в- *endptr. Поэтому в- endptrсвободно можно передать NULL.
- PGTYPESnumeric_to_asc
- Возвращает указатель на строку, выделенную функцией - mallocи содержащую строковое представление значения- numчислового типа.- char *PGTYPESnumeric_to_asc(numeric *num, int dscale); - Числовое значение будет выводиться с заданным в - dscaleколичеством цифр после запятой, округлённое при необходимости. Результат нужно освободить функцией- PGTYPESchar_free().
- PGTYPESnumeric_add
- Суммирует две числовые переменные и возвращает результат в третьей. - int PGTYPESnumeric_add(numeric *var1, numeric *var2, numeric *result); - Эта функция суммирует переменные - var1и- var2в результирующую переменную- result. Функция возвращает 0 в случае успеха и -1 при ошибке.
- PGTYPESnumeric_sub
- Вычисляет разность двух числовых переменных и возвращает результат в третьей. - int PGTYPESnumeric_sub(numeric *var1, numeric *var2, numeric *result); - Эта функция вычитает переменную - var2из- var1. Результат операции помещается в переменную- result. Функция возвращает 0 в случае успеха и -1 при ошибке.
- PGTYPESnumeric_mul
- Перемножает две числовые переменные и возвращает результат в третьей. - int PGTYPESnumeric_mul(numeric *var1, numeric *var2, numeric *result); - Эта функция перемножает переменные - var1и- var2. Результат операции сохраняется в переменной- result. Функция возвращает 0 в случае успеха и -1 при ошибке.
- PGTYPESnumeric_div
- Вычисляет частное двух числовых переменных и возвращает результат в третьей. - int PGTYPESnumeric_div(numeric *var1, numeric *var2, numeric *result); - Эта функция делит переменную - var1на- var2. Результат операции сохраняется в переменной- result. Функция возвращает 0 в случае успеха и -1 при ошибке.
- PGTYPESnumeric_cmp
- Сравнивает две числовые переменные. - int PGTYPESnumeric_cmp(numeric *var1, numeric *var2) - Эта функция производит сравнение двух числовых переменных. При ошибке возвращается - INT_MAX. В случае успеха функция возвращает одно из трёх возможных значений:- 1, если - var1больше- var2
- -1, если - var1меньше- var2
- 0, если - var1и- var2равны
 
- PGTYPESnumeric_from_int
- Преобразует переменную int в переменную numeric. - int PGTYPESnumeric_from_int(signed int int_val, numeric *var); - Эта функция принимает целочисленную переменную со знаком типа signed int и сохраняет её значение в переменной - varтипа numeric. Функция возвращает 0 в случае успеха и -1 при ошибке.
- PGTYPESnumeric_from_long
- Преобразует переменную long int в переменную numeric. - int PGTYPESnumeric_from_long(signed long int long_val, numeric *var); - Эта функция принимает целочисленную переменную со знаком типа signed long int и сохраняет её значение в переменной - varтипа numeric. Функция возвращает 0 в случае успеха и -1 при ошибке.
- PGTYPESnumeric_copy
- Копирует одну числовую переменную в другую. - int PGTYPESnumeric_copy(numeric *src, numeric *dst); - Эта функция копирует значение переменной, на которую указывает - src, в переменную, на которую указывает- dst. Она возвращает 0 в случае успеха и -1 при ошибке.
- PGTYPESnumeric_from_double
- Преобразует переменную типа double в переменную numeric. - int PGTYPESnumeric_from_double(double d, numeric *dst); - Эта функция принимает переменную типа double и сохраняет преобразованное значение в переменной, на которую указывает - dst. Она возвращает 0 в случае успеха и -1 при ошибке.
- PGTYPESnumeric_to_double
- Преобразует переменную типа numeric в переменную double. - int PGTYPESnumeric_to_double(numeric *nv, double *dp) - Эта функция преобразует значение типа numeric переменной, на которую указывает - nv, в переменную типа double, на которую указывает- dp. Она возвращает 0 в случае успеха и -1 при ошибке, в том числе при переполнении. Если происходит переполнение, в глобальной переменной- errnoдополнительно устанавливается значение- PGTYPES_NUM_OVERFLOW.
- PGTYPESnumeric_to_int
- Преобразует переменную типа numeric в переменную int. - int PGTYPESnumeric_to_int(numeric *nv, int *ip); - Эта функция преобразует значение типа numeric переменной, на которую указывает - nv, в целочисленную переменную, на которую указывает- ip. Она возвращает 0 в случае успеха и -1 при ошибке, в том числе при переполнении. Если происходит переполнение, в глобальной переменной- errnoдополнительно устанавливается значение- PGTYPES_NUM_OVERFLOW.
- PGTYPESnumeric_to_long
- Преобразует переменную типа numeric в переменную long. - int PGTYPESnumeric_to_long(numeric *nv, long *lp); - Эта функция преобразует значение типа numeric переменной, на которую указывает - nv, в целочисленную переменную типа long, на которую указывает- lp. Она возвращает 0 в случае успеха и -1 при ошибке, в том числе при переполнении. Если происходит переполнение, в глобальной переменной- errnoдополнительно устанавливается значение- PGTYPES_NUM_OVERFLOW.
- PGTYPESnumeric_to_decimal
- Преобразует переменную типа numeric в переменную decimal. - int PGTYPESnumeric_to_decimal(numeric *src, decimal *dst); - Эта функция преобразует значение типа numeric переменной, на которую указывает - src, в переменную типа decimal, на которую указывает- dst. Она возвращает 0 в случае успеха и -1 при ошибке, в том числе при переполнении. Если происходит переполнение, в глобальной переменной- errnoдополнительно устанавливается значение- PGTYPES_NUM_OVERFLOW.
- PGTYPESnumeric_from_decimal
- Преобразует переменную типа decimal в переменную numeric. - int PGTYPESnumeric_from_decimal(decimal *src, numeric *dst); - Эта функция преобразует значение типа decimal переменной, на которую указывает - src, в переменную типа numeric, на которую указывает- dst. Она возвращает 0 в случае успеха и -1 при ошибке. Так как тип decimal реализован как ограниченная версия типа numeric, при таком преобразовании переполнение невозможно.
35.6.3. Тип date
Тип date, реализованный в C, позволяет программам работать с данными типа date в SQL. Соответствующий тип сервера PostgreSQL описан в Разделе 8.5.
Для работы с типом date можно использовать следующие функции:
- PGTYPESdate_from_timestamp
- Извлекает часть даты из значения типа timestamp. - date PGTYPESdate_from_timestamp(timestamp dt); - Эта функция получает в единственном аргументе значение времени типа timestamp и возвращает извлечённую из него дату. 
- PGTYPESdate_from_asc
- Разбирает дату из её текстового представления. - date PGTYPESdate_from_asc(char *str, char **endptr); - Эта функция получает строку C char* - strи указатель на строку C char*- endptr. На данный момент ECPG всегда разбирает строку до конца, так что эта функция не может вернуть адрес первого недопустимого символа в- *endptr. Поэтому в- endptrсвободно можно передать NULL.- Заметьте, что эта функция всегда подразумевает формат дат MDY (месяц-день-год) и никакой переменной для изменения этого формата в ECPG нет. - Все допустимые форматы ввода перечислены в Таблице 35.2. - Таблица 35.2. Допустимые форматы ввода для - PGTYPESdate_from_asc- Ввод - Результат - January 8, 1999- January 8, 1999- 1999-01-08- January 8, 1999- 1/8/1999- January 8, 1999- 1/18/1999- January 18, 1999- 01/02/03- February 1, 2003- 1999-Jan-08- January 8, 1999- Jan-08-1999- January 8, 1999- 08-Jan-1999- January 8, 1999- 99-Jan-08- January 8, 1999- 08-Jan-99- January 8, 1999- 08-Jan-06- January 8, 2006- Jan-08-99- January 8, 1999- 19990108- ISO 8601; January 8, 1999- 990108- ISO 8601; January 8, 1999- 1999.008- год и день года- J2451187- Юлианский день- January 8, 99 BC- 99 год до нашей эры
- PGTYPESdate_to_asc
- Возвращает текстовое представление переменной типа date. - char *PGTYPESdate_to_asc(date dDate); - Эта функция получает в качестве единственного параметра дату - dDateи выводит её в виде- 1999-01-18, то есть в формате- YYYY-MM-DD. Результат необходимо освободить функцией- PGTYPESchar_free().
- PGTYPESdate_julmdy
- Извлекает значения дня, месяца и года из переменной типа date. - void PGTYPESdate_julmdy(date d, int *mdy); - Эта функция получает дату - dи указатель на 3 целочисленных значения- mdy. Имя переменной указывает на порядок значений: в- mdy[0]записывается номер месяца, в- mdy[1]— номер дня, а в- mdy[2]— год.
- PGTYPESdate_mdyjul
- Образует значение даты из массива 3 целых чисел, задающих день, месяц и год даты. - void PGTYPESdate_mdyjul(int *mdy, date *jdate); - Эта функция получает в первом аргументе массив из 3 целых чисел ( - mdy), а во втором указатель на переменную типа date, в которую будет помещён результат операции.
- PGTYPESdate_dayofweek
- Возвращает число, представляющее день недели для заданной даты. - int PGTYPESdate_dayofweek(date d); - Эта функция принимает в единственном аргументе переменную - dтипа date и возвращает целое число, выражающее день недели для этой даты.- 0 — Воскресенье 
- 1 — Понедельник 
- 2 — Вторник 
- 3 — Среда 
- 4 — Четверг 
- 5 — Пятница 
- 6 — Суббота 
 
- PGTYPESdate_today
- Выдаёт текущую дату. - void PGTYPESdate_today(date *d); - Эта функция получает указатель на переменную ( - d) типа date, в которую будет записана текущая дата.
- PGTYPESdate_fmt_asc
- Преобразует переменную типа date в текстовое представление по маске формата. - int PGTYPESdate_fmt_asc(date dDate, char *fmtstring, char *outbuf); - Эта функция принимает дату для преобразования ( - dDate), маску формата (- fmtstring) и строку, в которую будет помещено текстовое представление даты (- outbuf).- В случае успеха возвращается 0, а в случае ошибки — отрицательное значение. - В строке формата можно использовать следующие коды полей: - dd— Номер дня в месяце.
- mm— Номер месяца в году.
- yy— Номер года в виде двух цифр.
- yyyy— Номер года в виде четырёх цифр.
- ddd— Название дня недели (сокращённое).
- mmm— Название месяца (сокращённое).
 - Все другие символы копируются в выводимую строку 1:1. - В Таблице 35.3 перечислены несколько возможных форматов. Это даёт представление, как можно использовать эту функцию. Все строки вывода даны для одной даты: 23 ноября 1959 г. - Таблица 35.3. Допустимые форматы ввода для - PGTYPESdate_fmt_asc- Формат - Результат - mmddyy- 112359- ddmmyy- 231159- yymmdd- 591123- yy/mm/dd- 59/11/23- yy mm dd- 59 11 23- yy.mm.dd- 59.11.23- .mm.yyyy.dd.- .11.1959.23.- mmm. dd, yyyy- Nov. 23, 1959- mmm dd yyyy- Nov 23 1959- yyyy dd mm- 1959 23 11- ddd, mmm. dd, yyyy- Mon, Nov. 23, 1959- (ddd) mmm. dd, yyyy- (Mon) Nov. 23, 1959
- PGTYPESdate_defmt_asc
- Преобразует строку C - char*в значение типа date по маске формата.- int PGTYPESdate_defmt_asc(date *d, char *fmt, char *str); - Эта функция принимает указатель на переменную типа date ( - d), в которую будет помещён результат операции, маску формата для разбора даты (- fmt) и строку C char*, содержащую текстовое представление даты (- str). Ожидается, что текстовое представление будет соответствовать маске формата. Однако это соответствие не обязательно должно быть точным. Данная функция анализирует только порядок элементов и ищет в нём подстроки- yyили- yyyy, обозначающие позицию года, подстроку- mm, обозначающую позицию месяца, и- dd, обозначающую позицию дня.- В Таблица 35.4 перечислены несколько возможных форматов. Это даёт представление, как можно использовать эту функцию. - Таблица 35.4. Допустимые форматы ввода для - rdefmtdate- Формат - Строка - Результат - ddmmyy- 21-2-54- 1954-02-21- ddmmyy- 2-12-54- 1954-12-02- ddmmyy- 20111954- 1954-11-20- ddmmyy- 130464- 1964-04-13- mmm.dd.yyyy- MAR-12-1967- 1967-03-12- yy/mm/dd- 1954, February 3rd- 1954-02-03- mmm.dd.yyyy- 041269- 1969-04-12- yy/mm/dd- In the year 2525, in the month of July, mankind will be alive on the 28th day- 2525-07-28- dd-mm-yy- I said on the 28th of July in the year 2525- 2525-07-28- mmm.dd.yyyy- 9/14/58- 1958-09-14- yy/mm/dd- 47/03/29- 1947-03-29- mmm.dd.yyyy- oct 28 1975- 1975-10-28- mmddyy- Nov 14th, 1985- 1985-11-14
35.6.4. Тип timestamp
Тип timestamp, реализованный в C, позволяет программам работать с данными типа timestamp в SQL. Соответствующий тип сервера PostgreSQL описан в Разделе 8.5.
Для работы с типом timestamp можно использовать следующие функции:
- PGTYPEStimestamp_from_asc
- Разбирает значение даты/времени из текстового представления в переменную типа timestamp. - timestamp PGTYPEStimestamp_from_asc(char *str, char **endptr); - Эта функция получает строку ( - str), которую нужно разобрать, и указатель на строку C char* (- endptr). На данный момент ECPG всегда разбирает строку до конца, так что эта функция не может вернуть адрес первого недопустимого символа в- *endptr. Поэтому в- endptrсвободно можно передать NULL.- В случае успеха эта функция возвращает разобранное время, а в случае ошибки возвращается - PGTYPESInvalidTimestampи в- errnoустанавливается значение- PGTYPES_TS_BAD_TIMESTAMP. См. замечание относительно- PGTYPESInvalidTimestamp.- Вообще вводимая строка может содержать допустимое указание даты, пробельные символы и допустимое указание времени в любом сочетании. Заметьте, что часовые пояса ECPG не поддерживает. Эта функция может разобрать их, но не задействует их в вычислениях как это делает, например, сервер PostgreSQL. Указания часового пояса во вводимой строке просто игнорируются. - В Таблица 35.5 приведены несколько примеров вводимых строк. - Таблица 35.5. Допустимые форматы ввода для - PGTYPEStimestamp_from_asc- Ввод - Результат - 1999-01-08 04:05:06- 1999-01-08 04:05:06- January 8 04:05:06 1999 PST- 1999-01-08 04:05:06- 1999-Jan-08 04:05:06.789-8- 1999-01-08 04:05:06.789 (указание часового пояса игнорируется)- J2451187 04:05-08:00- 1999-01-08 04:05:00 (указание часового пояса игнорируется)
- PGTYPEStimestamp_to_asc
- Преобразует значение даты в строку C char*. - char *PGTYPEStimestamp_to_asc(timestamp tstamp); - Эта функция принимает в качестве единственного аргумента - tstampзначение типа timestamp и возвращает размещённую в памяти строку, содержащую текстовое представление даты/времени. Результат необходимо освободить функцией- PGTYPESchar_free().
- PGTYPEStimestamp_current
- Получает текущее время. - void PGTYPEStimestamp_current(timestamp *ts); - Эта функция получает текущее время и сохраняет его в переменной типа timestamp, на которую указывает - ts.
- PGTYPEStimestamp_fmt_asc
- Преобразует переменную типа timestamp в строку C char* по маске формата. - int PGTYPEStimestamp_fmt_asc(timestamp *ts, char *output, int str_len, char *fmtstr); - Эта функция получает в первом аргументе ( - ts) указатель на переменную типа timestamp, а в последующих указатель на буфер вывода (- output), максимальную длину строки, которую может принять буфер (- str_len), и маску формата, с которой будет выполняться преобразование (- fmtstr).- В случае успеха возвращается 0, а в случае ошибки — отрицательное значение. - В маске формата можно использовать коды формата, перечисленные ниже. Эти же коды принимает функция - strftimeиз библиотеки libc. Любые символы, не относящиеся к кодам формата, будут просто скопированы в буфер вывода.- %A— заменяется локализованным представлением полного названия дня недели.
- %a— заменяется локализованным представлением сокращённого названия дня недели.
- %B— заменяется локализованным представлением полного названия месяца.
- %b— заменяется локализованным представлением сокращённого названия месяца.
- %C— заменяется столетием (год / 100) в виде десятичного числа; одиночная цифра предваряется нулём.
- %c— заменяется локализованным представлением даты и времени.
- %D— равнозначно- %m/%d/%y.
- %d— заменяется днём месяца в виде десятичного числа (01-31).
- %E*- %O*— расширения локали POSIX. Последовательности- %Ec- %EC- %Ex- %EX- %Ey- %EY- %Od- %Oe- %OH- %OI- %Om- %OM- %OS- %Ou- %OU- %OV- %Ow- %OW- %Oyдолжны выводить альтернативные представления.- Кроме того, альтернативные названия месяцев представляет код формата - %OB(используется отдельно, без упоминания дня).
- %e— заменяется днём в виде десятичного числа (1-31); одиночная цифра предваряется пробелом.
- %F— равнозначно- %Y-%m-%d.
- %G— заменяется годом в виде десятичного числа (со столетием). При этом годом считается тот, что содержит наибольшую часть недели (дни недели начинаются с понедельника).
- %g— заменяется тем же годом, что и- %G, но в виде десятичного числа без столетия (00-99).
- %H— заменяется часами (в 24-часовом формате) в виде десятичного числа (00-23).
- %h— равнозначно- %b.
- %I— заменяется часами (в 12-часовом формате) в виде десятичного числа (01-12).
- %j— заменяется днём года в виде десятичного числа (001-366).
- %k— заменяется часами (в 24-часовом формате) в виде десятичного числа (0-23); одиночная цифра предваряется пробелом.
- %l— заменяется часами (в 12-часовом формате) в виде десятичного числа (1-12); одиночная цифра предваряется пробелом.
- %M— заменяется минутами в виде десятичного числа (00-59).
- %m— заменяется номером месяца в виде десятичного числа (01-12).
- %n— заменяется символом новой строки.
- %O*— равнозначно- %E*.
- %p— заменяется локализованным представлением «до полудня» или «после полудня» в зависимости от времени.
- %R— равнозначно- %H:%M.
- %r— равнозначно- %I:%M:%S %p.
- %S— заменяется секундами в виде десятичного числа (00-60).
- %s— заменяется числом секунд с начала эпохи, по мировому времени (UTC).
- %T— равнозначно- %H:%M:%S
- %t— заменяется символом табуляции.
- %U— заменяется номером недели в году (первым днём недели считается воскресенье) в виде десятичного числа (00-53).
- %u— заменяется номером дня недели (первым днём недели считается понедельник) в виде десятичного числа (1-7).
- %V— заменяется номером недели в году (первым днём недели считается понедельник) в виде десятичного числа (01-53). Если к недели, включающей 1 января, относятся 4 или больше дней нового года, она считается неделей с номером 1; в противном случае это последняя неделя предыдущего года, а неделей под номером 1 будет следующая.
- %v— равнозначно- %e-%b-%Y.
- %W— заменяется номером недели в году (первым днём недели считается понедельник) в виде десятичного числа (00-53).
- %w— заменяется номером дня недели (первым днём недели считается воскресенье) в виде десятичного числа (0-6).
- %X— заменяется локализованным представлением времени.
- %x— заменяется локализованным представлением даты.
- %Y— заменяется годом со столетием в виде десятичного числа.
- %y— заменяется годом без столетия в виде десятичного числа (00-99).
- %Z— заменяется названием часового пояса.
- %z— заменяется смещением часового пояса от UTC; ведущий знак плюс обозначает смещение к востоку от UTC, а знак минус — к западу, часы и минуты задаются парами цифр без разделителя между ними (эта форма установлена для даты в RFC 822).
- %+— заменяется локализованным представлением даты и времени.
- %-*— расширение GNU libc. Отключает дополнение чисел по ширине при выводе.
- $_* — расширение GNU libc. Явно включает дополнение пробелами. 
- %0*— расширение GNU libc. Явно включает дополнение нулями.
- %%— заменяется символом- %.
 
- PGTYPEStimestamp_sub
- Вычитает одно значение времени из другого и сохраняет результат в переменной типа interval. - int PGTYPEStimestamp_sub(timestamp *ts1, timestamp *ts2, interval *iv); - Эта функция вычитает значение типа timestamp, на которое указывает - ts2, из значения timestamp, на которое указывает- ts1, и сохраняет результат в переменной типа interval, на которую указывает- iv.- В случае успеха возвращается 0, а в случае ошибки — отрицательное значение. 
- PGTYPEStimestamp_defmt_asc
- Разбирает значение типа timestamp из текстового представления с заданной маской формата. - int PGTYPEStimestamp_defmt_asc(char *str, char *fmt, timestamp *d); - Эта функция получает текстовое представление даты/времени в переменной - str, а также маску формата для разбора в переменной- fmt. Результат будет сохранён в переменной, на которую указывает- d.- Если вместо маски формата - fmtпередаётся NULL, эта функция переходит к стандартной маске форматирования, а именно:- %Y-%m-%d %H:%M:%S.- Данная функция является обратной к функции - PGTYPEStimestamp_fmt_asc. Обратитесь к её документации, чтобы узнать о возможных вариантах маски формата.
- PGTYPEStimestamp_add_interval
- Добавляет переменную типа interval к переменной типа timestamp. - int PGTYPEStimestamp_add_interval(timestamp *tin, interval *span, timestamp *tout); - Эта функция получает указатель на переменную - tinтипа timestamp и указатель на переменную- spanтипа interval. Она добавляет временной интервал к значению даты/времени и сохраняет полученную дату/время в переменной типа timestamp, на которую указывает- tout.- В случае успеха возвращается 0, а в случае ошибки — отрицательное значение. 
- PGTYPEStimestamp_sub_interval
- Вычитает переменную типа interval из переменной типа timestamp. - int PGTYPEStimestamp_sub_interval(timestamp *tin, interval *span, timestamp *tout); - Эта функция вычитает значение типа interval, на которое указывает - span, из значения типа timestamp, на которое указывает- tin, и сохраняет результат в переменной, на которую указывает- tout.- В случае успеха возвращается 0, а в случае ошибки — отрицательное значение. 
35.6.5. Тип interval
Тип interval, реализованный в C, позволяет программам работать с данными типа interval в SQL. Соответствующий тип сервера PostgreSQL описан в Разделе 8.5.
Для работы с типом interval можно использовать следующие функции:
- PGTYPESinterval_new
- Возвращает указатель на новую переменную interval, размещённую в памяти. - interval *PGTYPESinterval_new(void); 
- PGTYPESinterval_free
- Освобождает место, занимаемое ранее размещённой в памяти переменной типа interval. - void PGTYPESinterval_free(interval *intvl); 
- PGTYPESinterval_from_asc
- Разбирает значение типа interval из его текстового представления. - interval *PGTYPESinterval_from_asc(char *str, char **endptr); - Эта функция разбирает входную строку - strи возвращает указатель на размещённую в памяти переменную типа interval. На данный момент ECPG всегда разбирает строку до конца, так что эта функция не может вернуть адрес первого недопустимого символа в- *endptr. Поэтому в- endptrсвободно можно передать NULL.
- PGTYPESinterval_to_asc
- Преобразует переменную типа interval в текстовое представление. - char *PGTYPESinterval_to_asc(interval *span); - Эта функция преобразует переменную типа interval, на которую указывает - span, в строку C char*. Её вывод выглядит примерно так:- @ 1 day 12 hours 59 mins 10 secs. Результат необходимо освободить функцией- PGTYPESchar_free().
- PGTYPESinterval_copy
- Копирует переменную типа interval. - int PGTYPESinterval_copy(interval *intvlsrc, interval *intvldest); - Эта функция копирует переменную типа interval, на которую указывает - intvlsrc, в переменную, на которую указывает- intvldest. Заметьте, что для целевой переменной необходимо предварительно выделить память.
35.6.6. Тип decimal
Тип decimal похож на тип numeric, однако его максимальная точность ограничена 30 значащими цифрами. В отличие от типа numeric, который можно создать только в области кучи, тип decimal можно создать и в стеке, и в области кучи (посредством функций PGTYPESdecimal_new и PGTYPESdecimal_free). Для работы с типом decimal есть много других функций, подключаемых в режиме совместимости с Informix, описанном в Разделе 35.15.
Для работы с типом decimal можно использовать следующие функции (содержащиеся не в библиотеке libcompat). 
- PGTYPESdecimal_new
- Запрашивает указатель на новую переменную decimal, размещённую в памяти. - decimal *PGTYPESdecimal_new(void); 
- PGTYPESdecimal_free
- Освобождает переменную типа decimal, высвобождая всю её память. - void PGTYPESdecimal_free(decimal *var); 
35.6.7. Значения errno, которые устанавливает pgtypeslib
- PGTYPES_NUM_BAD_NUMERIC
- Аргумент должен содержать переменную типа numeric (либо указывать на переменную типа numeric), но представление этого типа в памяти оказалось некорректным. 
- PGTYPES_NUM_OVERFLOW
- Произошло переполнение. Так как тип numeric может принимать значения практически любой точности, при преобразовании этого типа в другие типы возможно переполнение. 
- PGTYPES_NUM_UNDERFLOW
- Произошло антипереполнение. Так как тип numeric может принимать значения практически любой точности, при преобразовании переменной этого типа в другие типы возможно антипереполнение. 
- PGTYPES_NUM_DIVIDE_ZERO
- Имела место попытка деления на ноль. 
- PGTYPES_DATE_BAD_DATE
- Функции - PGTYPESdate_from_ascпередана некорректная строка даты.
- PGTYPES_DATE_ERR_EARGS
- Функции - PGTYPESdate_defmt_ascпереданы некорректные аргументы.
- PGTYPES_DATE_ERR_ENOSHORTDATE
- В строке, переданной функции - PGTYPESdate_defmt_asc, оказался неправильный компонент даты.
- PGTYPES_INTVL_BAD_INTERVAL
- Функции - PGTYPESinterval_from_ascпередана некорректная строка, задающая интервал, либо функции- PGTYPESinterval_to_ascпередано некорректное значение интервала.
- PGTYPES_DATE_ERR_ENOTDMY
- Обнаружено несоответствие при выводе компонентов день/месяц/год в функции - PGTYPESdate_defmt_asc.
- PGTYPES_DATE_BAD_DAY
- Функция - PGTYPESdate_defmt_ascобнаружила некорректное значение дня месяца.
- PGTYPES_DATE_BAD_MONTH
- Функция - PGTYPESdate_defmt_ascобнаружила некорректное значение месяца.
- PGTYPES_TS_BAD_TIMESTAMP
- Функции - PGTYPEStimestamp_from_ascпередана некорректная строка даты/времени, либо функции- PGTYPEStimestamp_to_ascпередано некорректное значение типа timestamp.
- PGTYPES_TS_ERR_EINFTIME
- Значение типа timestamp, представляющее бесконечность, получено в недопустимом контексте. 
35.6.8. Специальные константы pgtypeslib
- PGTYPESInvalidTimestamp
- Значение типа timestamp, представляющее недопустимое время. Это значение возвращает функция - PGTYPEStimestamp_from_ascпри ошибке разбора. Заметьте, что вследствие особенности внутреннего представления типа- timestamp, значение- PGTYPESInvalidTimestampв то же время представляет корректное время (- 1899-12-31 23:59:59). Поэтому для выявления ошибок необходимо, чтобы приложение не только сравнивало результат функции с- PGTYPESInvalidTimestamp, но и проверяло условие- errno != 0после каждого вызова- PGTYPEStimestamp_from_asc.