Символы пробелов в полях Char, VarChar

2011-03-07 Пенетрантность AZDesign
Firebird 2.5.0.26074 (x64)

Делаем табличку:
Create table Words
  (Word  VarChar(250)  character set WIN1251  Unique);

Затем вставляем строку:

Insert into Words(Word) values('');

 и еще одну:

Insert into Words(Word) values('');

получаем:
Statement failed, SQLSTATE = 23000
violation of PRIMARY or UNIQUE KEY constraint INTEG_3 on table Words

Замена VarChar на Char ничего не меняет.
т.е. строки состоящие из один пробелов считаются одинаковыми, независимо от
количества пробелов в каждой из них.

Это так и должно быть или баг?
Хелен Борри пишет, что в Char завершающие пробелы не являются значащими
(т.е. отбрасываются), а в VarChar завершающие пробелы являются значащими
(т.е. сохраняются).
На практике получается не так.


--
View this message in context: 
http://firebird.1100200.n4.nabble.com/Char-VarChar-tp3338553p3338553.html
Sent from the firebird-russian mailing list archive at Nabble.com.

Re: Символы пробелов в полях Char, VarChar

2011-03-07 Пенетрантность Vlad Khorsun

AZDesign wrote in message ...

Firebird 2.5.0.26074 (x64)

Делаем табличку:
Create table Words
 (Word  VarChar(250)  character set WIN1251  Unique);

Затем вставляем строку:

Insert into Words(Word) values('');

и еще одну:

Insert into Words(Word) values('');

получаем:
Statement failed, SQLSTATE = 23000
violation of PRIMARY or UNIQUE KEY constraint INTEG_3 on table Words

Замена VarChar на Char ничего не меняет.
т.е. строки состоящие из один пробелов считаются одинаковыми, независимо от
количества пробелов в каждой из них.

Это так и должно быть или баг?


   Так и должно быть. Стандарт.


Хелен Борри пишет, что в Char завершающие пробелы не являются значащими
(т.е. отбрасываются), а в VarChar завершающие пробелы являются значащими
(т.е. сохраняются).
На практике получается не так.


   Хранение и сравнение не есть одно и то же, не нужно их путать. Кроме того, 
CHAR
всегда дополняется пробелами до объявленной длины. А как они хранятся тебя не
должно волновать.

--
Хорсун Влад 





Re: Символы пробелов в полях Char, VarChar

2011-03-07 Пенетрантность AZDesign

Vlad Khorsun wrote:
 
 Это так и должно быть или баг?
 
 Так и должно быть. Стандарт.
 
 Хелен Борри пишет, что в Char завершающие пробелы не являются значащими
 (т.е. отбрасываются), а в VarChar завершающие пробелы являются значащими
 (т.е. сохраняются).
 На практике получается не так.
 
 Хранение и сравнение не есть одно и то же, не нужно их путать. Кроме
 того, CHAR
 всегда дополняется пробелами до объявленной длины. А как они хранятся тебя
 не
 должно волновать.
 

В принципе меня не волнует как они хранятся. Просто мне нужно чтобы в
справочнике отличались две строки - одна пустая строка '', а другая
состоящая из 1 ' ' (или нескольких пробелов).
Сейчас строки состоящие только из пробелов при сравнении равны друг другу,
хотя по факту, одна например, состоит из 1 пробела, а другая из 100
пробелов.


--
View this message in context: 
http://firebird.1100200.n4.nabble.com/Char-VarChar-tp3338553p3338714.html
Sent from the firebird-russian mailing list archive at Nabble.com.

Re: Символы пробелов в полях Char, VarChar

2011-03-07 Пенетрантность Vlad Khorsun

AZDesign wrote ...


В принципе меня не волнует как они хранятся. Просто мне нужно чтобы в
справочнике отличались две строки - одна пустая строка '', а другая
состоящая из 1 ' ' (или нескольких пробелов).
Сейчас строки состоящие только из пробелов при сравнении равны друг другу,
хотя по факту, одна например, состоит из 1 пробела, а другая из 100
пробелов.


а) храни нуллы вместо пустых строк
б) сравнивай не только содержимое, но и его длину, при совпадении
в) дописывай не пробельный символ в конец строки и игнорируй его при извлечении
г) пересмотри задачу, чтобы не было таких проблем

--
Хорсун Влад 





Re[2]: Символы пробелов в полях Char, VarChar

2011-03-07 Пенетрантность Sergey Mereutsa
Привет!

 В принципе меня не волнует как они хранятся. Просто мне нужно чтобы в
 справочнике отличались две строки - одна пустая строка '', а другая
 состоящая из 1 ' ' (или нескольких пробелов).
 Сейчас строки состоящие только из пробелов при сравнении равны друг другу,
 хотя по факту, одна например, состоит из 1 пробела, а другая из 100
 пробелов.

 а) храни нуллы вместо пустых строк
 б) сравнивай не только содержимое, но и его длину, при совпадении
 в) дописывай не пробельный символ в конец строки и игнорируй его при 
 извлечении
 г) пересмотри задачу, чтобы не было таких проблем

Если товарищ хранит строки на Whitespace - 
http://en.wikipedia.org/wiki/Whitespace_%28programming_language%29
- то ему не очень сильно поможет твой совет.

Я бы посоветовал ему обрамлять кавычками пустые строки - т.е.
добавлять именно кавычки по краям как часть строки. А в проге их
убирать.

Но вообще - не могу себе представить задачу, где надо 5 пробелов
отличать от 6 :)

-- 
Best regards,
 Sergeymailto:gebele...@gmail.com




Re: Re[2]: Символы пробелов в полях Char, VarChar

2011-03-07 Пенетрантность Vlad Khorsun

Sergey Mereutsa wrote in message ...


 В принципе меня не волнует как они хранятся. Просто мне нужно чтобы в
 справочнике отличались две строки - одна пустая строка '', а другая
 состоящая из 1 ' ' (или нескольких пробелов).
 Сейчас строки состоящие только из пробелов при сравнении равны друг другу,
 хотя по факту, одна например, состоит из 1 пробела, а другая из 100
 пробелов.

 а) храни нуллы вместо пустых строк
 б) сравнивай не только содержимое, но и его длину, при совпадении
 в) дописывай не пробельный символ в конец строки и игнорируй его при 
извлечении
 г) пересмотри задачу, чтобы не было таких проблем

Если товарищ хранит строки на Whitespace - 
http://en.wikipedia.org/wiki/Whitespace_%28programming_language%29
- то ему не очень сильно поможет твой совет.


   Это ты специально такое выискивал ? %)


Я бы посоветовал ему обрамлять кавычками пустые строки - т.е.
добавлять именно кавычки по краям как часть строки. А в проге их
убирать.


   Чем это отличается от (в) ?


о вообще - не могу себе представить задачу, где надо 5 пробелов
отличать от 6 :)


   Именно.

--
Хорсун Влад 





Re[4]: Символы пробелов в полях Char, VarChar

2011-03-07 Пенетрантность Sergey Mereutsa
Привет!

 Если товарищ хранит строки на Whitespace - 
 http://en.wikipedia.org/wiki/Whitespace_%28programming_language%29
 - то ему не очень сильно поможет твой совет.

 Это ты специально такое выискивал ? %)

Угу. Постановка задачи навела на мысль :)

 Я бы посоветовал ему обрамлять кавычками пустые строки - т.е.
 добавлять именно кавычки по краям как часть строки. А в проге их
 убирать.

 Чем это отличается от (в) ?

Да кагбе ничем. Те же яйца, только в профиль.


:)




-- 
Best regards,
 Sergeymailto:gebele...@gmail.com




Re: Символы пробелов в полях Char, VarChar

2011-03-07 Пенетрантность AZDesign
1) для решения проблемы я храню строку из 1 пробела как #32
Остальное нужно для единообразия действий и понимания процесса.
2) читаем Хелен Борри:
Использование типов фиксированной длины не рекомендуется для данных,
которые могут содержать ЗНАЧИМЫЕ конечные символы пробелов, или для
элементов, чья фактическая длина может сильно изменяться. (стр.204)
Символьный тип переменной длины используется для хранения ТЕКСТОВ, потому
что размер хранимой структуры равен ФАКТИЧЕСКОМУ РАЗМЕРУ ДАННЫХ плюс два
байта. ВСЕ СИМВОЛЫ, введенные в поле переменной длины, ТРАКТУЮТСЯ КАК
ЗНАЧИМЫЕ, ВКЛЮЧАЯ НАЧАЛЬНЫЕ и КОНЕЧНЫЕ ПРОБЕЛЬНЫЕ СИМВОЛЫ (стр.205)

На самом деле и в случае CHAR, и в случае VARCHAR:
- строка пробелов любой длины рассматривается как пустая, т.е. функция
OCTET_LENGTH дает 0
- конечные пробельные символы ВСЕГДА НЕ ЗНАЧИМЫЕ, т.е. '   #' = '   #   ',
(их длина одинаковая), что не соответствует вышеописанному.

Задача для этого простая - сжатие текста. При составлении словаря возникает
проблема хранения строк состоящих только из пробелов. В таком случае для
всех слов нужно добавлять конечный символ при записи и удалять его при
чтении. А так как в словаре могут быть слова типа A+B+C, то вся логика
обработки уходит на клиента или в UDF, что не есть хорошо.

 

--
View this message in context: 
http://firebird.1100200.n4.nabble.com/Char-VarChar-tp3338553p3340644.html
Sent from the firebird-russian mailing list archive at Nabble.com.

Re: Символы пробелов в полях Char, VarChar

2011-03-07 Пенетрантность Dmitry Yemanov

08.03.2011 7:52, AZDesign пишет:


- строка пробелов любой длины рассматривается как пустая, т.е. функция
OCTET_LENGTH дает 0


У меня почему-то не дает. Что я делаю не так?


- конечные пробельные символы ВСЕГДА НЕ ЗНАЧИМЫЕ, т.е. '   #' = '   #   ',
(их длина одинаковая), что не соответствует вышеописанному.


Не значимые они при сравнении. Они просто игнорируются. Таково 
требование стандарта, независимо от типа данных.


Но пробелы в строке таки хранятся. И прочитав данные на клиента и 
сравнив их вручную, пробелы станут значимыми. Да и на сравнении свет 
клином не сошелся. Длина этих пробелов очень даже учитывается, попробуй 
например конкатенацию - вот они родные и вылезли. Это считается 
незначимыми в твоем понимании?


Просто текст в книге несколько неоднозначен. Написано там про 
особенности хранения пробелов в строках разных типов, а не про их 
сравнение SQL-операторами.



--
Дмитрий Еманов