loading..
Русский    English
05:19
листать

О неявном преобразовании типов в SQL Server стр. 2

Итак, реально мы имеем то, что сравниваться могут значения одного типа. Для преобразования типов стандарт предлагает функцию CAST. То есть в общем случае мы должны преобразовать сравниваемые значения к одному типу, а затем уже выполнять операцию сравнения (или присвоения). Что же произойдет, если мы переменной (или столбцу) одного типа просто присвоим значение другого типа? Рассмотрим простой пример кода на T-SQL (в примерах используется SQL Server 2000):

  1. DECLARE @vc VARCHAR(10), @mn MONEY, @ft FLOAT
  2. SELECT @vc = '499.99'
  3. PRINT @vc
  4. SELECT @ft = @vc
  5. PRINT @ft

Здесь мы описывает три переменные соответственно строкового типа (VARCHAR), денежного типа (MONEY) и числа с плавающей точкой (FLOAT). Далее строковой переменной присваиваем константу соответствующего типа, а затем присваиваем переменной типа FLOAT значение строковой переменной. В результате получаем два одинаковых результата — 499.99 (оператор PRINT осуществляет сообщения вывод на консоль). То, что произошло, называется неявным преобразованием типов, то есть строковое значение — ‘499.99’ было автоматически приведено к типу FLOAT и присвоено переменной @ft.

Добавим в конец кода еще пару строк:

  1. SELECT @mn = @vc
  2. PRINT @mn

В результате получим два похожих сообщения об ошибке:

Implicit conversion from data type varchar to money is not allowed. Use the CONVERT function to run this query.

и

Implicit conversion from data type money to nvarchar is not allowed. Use the CONVERT function to run this query.

в одном из которых говорится о том, что неявное преобразование типа VARCHAR к типу MONEY не допускается, а в другом — о недопустимости и обратного преобразования. Как и следовало ожидать, нам предлагается использовать явное преобразование с помощи функции CONVERT. Однако чтобы быть ближе к стандарту, воспользуемся функцией CAST:

  1. SELECT @mn = CAST(@vc AS MONEY)
  2. PRINT @mn

От первого сообщения об ошибке мы избавились. Напрашивается вывод о том, что второе сообщение дает оператор PRINT. Попробуем заглянуть в справку. В  Электронная документация SQL Server Books OnlineBOL об операторе PRINT говорится, что переменная, которая может использоваться в этом операторе, должна быть любого допустимого строкового типа (CHAR или VARCHAR) или же должна неявно приводиться к этому типу.

Перепишем последнюю строку:

  1. PRINT CAST(@mn AS VARCHAR)

Все работает. Главный вывод, который мы отсюда извлекаем, заключается в том, что не все типы (даже если мы не видим особых причин тому) допускают неявное преобразование.

В частности, не выполняется неявное приведение типа MONEY к типам CHAR, VARCHAR, NCHAR, NVARCHAR и наоборот.

Примечание:

Следует отметить, что неявное преобразование к типу MONEY уже поддерживается в SQL Server в версиях 2005 и выше.

А теперь о причине, которая заставила нас написать так много слов. Из-за нашей неряшливости оказалось, что в основной и проверочной базе на сайте некоторые эквивалентные столбцы имели разные типы данных. Например, поле price в таблице РС имело тип FLOAT в одной базе и тип MONEY — в другой. В течение очень долгого времени это никак не влияло на работу сайта, но вдруг за последние несколько дней два наших участника решили использовать неявное преобразование типов в своих запросах с уже известным результатом.

Мы решили не ограничиваться извинениями, а написать этот опус об особенностях реализации, надеясь, что это принесет больше пользы. Что же касается типов, то замеченное расхождение уже приведено в соответствие.

Страницы: 1 2
Тэги:
ALL AVG battles CASE CAST CHAR CHARINDEX classes COALESCE Convert COUNT CTE DATEDIFF DATEPART DATETIME DELETE DISTINCT EXCEPT EXISTS EXTRACT FROM FULL JOIN GROUP BY Guadalcanal HAVING IN INNER JOIN insert INTERSECT ISNULL laptop LEFT LEFT OUTER JOIN LEN maker MAX MIN MySQL NOT IN NULL ORDER BY Outcome outcomes OVER PARTITION BY pc PIVOT PostgreSQL printer product Больше тэгов
Учебник обновлялся
несколько дней назад
©SQL-EX,2008 [Развитие] [Связь] [О проекте] [Ссылки] [Team]
Перепечатка материалов сайта возможна только с разрешения автора.
Rambler's Top100