Добро пожаловать в форум, Guest  >>   Войти | Регистрация | Поиск | Правила | В избранное | Подписаться
Все форумы / Microsoft SQL Server Новый топик    Ответить
 Аналог TRY_CAST в 2008?  [new]
vino
Member

Откуда:
Сообщений: 1191
Спрашиваю о возможности в пределах одного SELECT проигнорировать несколько ошибок конвертации varchar(19) в bigint.
Нужен аналог try_cast в версии MSSQL 2008.
Какие варианты возможны?
5 сен 13, 18:24    [14801413]     Ответить | Цитировать Сообщить модератору
 Re: Аналог TRY_CAST в 2008?  [new]
SQL2008
Member

Откуда: Москва
Сообщений: 4478
Функция
5 сен 13, 18:31    [14801446]     Ответить | Цитировать Сообщить модератору
 Re: Аналог TRY_CAST в 2008?  [new]
Гость333
Member

Откуда:
Сообщений: 3683
vino
Какие варианты возможны?

Зафигачить SQLCLR-функцию?
5 сен 13, 18:34    [14801457]     Ответить | Цитировать Сообщить модератору
 Re: Аналог TRY_CAST в 2008?  [new]
vino
Member

Откуда:
Сообщений: 1191
Гость333, CLR нельзя будет использовать.
5 сен 13, 19:02    [14801582]     Ответить | Цитировать Сообщить модератору
 Re: Аналог TRY_CAST в 2008?  [new]
Гость333
Member

Откуда:
Сообщений: 3683
vino
Гость333, CLR нельзя будет использовать.

Ну тогда вот: Как проверить число. Способ, которым вычисляется [BigIntValue], есть аналог TRY_CAST из varchar в bigint.
5 сен 13, 19:08    [14801602]     Ответить | Цитировать Сообщить модератору
 Re: Аналог TRY_CAST в 2008?  [new]
LexusR
Member

Откуда: Novosibirsk
Сообщений: 1887
create function dbo.fnConverToBigint(@input varchar(19))
RETURNS BIGINT
AS
BEGIN
  return(case when ((IsNumeric(@input) =1) and (abs(cast(@input as float))< 9223372036854775807))
    then cast(cast(@input as float) as BIGint)
	ELSE  null end)

END
go
 SELECT dbo.fnConverToBigint('42346755856969'),dbo.fnConverToBigint('435353_RWTRTE')
5 сен 13, 19:10    [14801608]     Ответить | Цитировать Сообщить модератору
 Re: Аналог TRY_CAST в 2008?  [new]
Гость333
Member

Откуда:
Сообщений: 3683
LexusR
create function dbo.fnConverToBigint(@input varchar(19))
RETURNS BIGINT
AS
BEGIN
  return(case when ((IsNumeric(@input) =1) and (abs(cast(@input as float))< 9223372036854775807))
    then cast(cast(@input as float) as BIGint)
	ELSE  null end)

END
go
 SELECT dbo.fnConverToBigint('42346755856969'),dbo.fnConverToBigint('435353_RWTRTE')

Не годится:
SELECT dbo.fnConverToBigint('42,34')
5 сен 13, 19:11    [14801615]     Ответить | Цитировать Сообщить модератору
 Re: Аналог TRY_CAST в 2008?  [new]
LexusR
Member

Откуда: Novosibirsk
Сообщений: 1887
ALTER function dbo.fnConverToBigint(@input varchar(19))
RETURNS BIGINT
AS
BEGIN
  return(case when ((IsNumeric(REPLACE(@input,',','.')) =1) and (abs(cast(REPLACE(@input,',','.') as float))< 9223372036854775807))
    then cast(cast(REPLACE(@input,',','.') as float) as BIGint)
	ELSE  null end)

END
go
 SELECT dbo.fnConverToBigint('42346755856969'),dbo.fnConverToBigint('435353_RWTRTE')
 SELECT dbo.fnConverToBigint('42,34')
5 сен 13, 19:15    [14801625]     Ответить | Цитировать Сообщить модератору
 Re: Аналог TRY_CAST в 2008?  [new]
vino
Member

Откуда:
Сообщений: 1191
LexusR
ALTER function dbo.fnConverToBigint(@input varchar(19))
RETURNS BIGINT
AS
BEGIN
  return(case when ((IsNumeric(REPLACE(@input,',','.')) =1) and (abs(cast(REPLACE(@input,',','.') as float))< 9223372036854775807))
    then cast(cast(REPLACE(@input,',','.') as float) as BIGint)
	ELSE  null end)

END
go
 SELECT dbo.fnConverToBigint('42346755856969'),dbo.fnConverToBigint('435353_RWTRTE')
 SELECT dbo.fnConverToBigint('42,34')

не сработает для
SELECT dbo.fnConverToBigint('$42,34')
5 сен 13, 19:30    [14801673]     Ответить | Цитировать Сообщить модератору
 Re: Аналог TRY_CAST в 2008?  [new]
Гость333
Member

Откуда:
Сообщений: 3683
LexusR,

А так?
SELECT dbo.fnConverToBigint('$42,34')

Вы не думайте, что по приведённой ссылке — какое-то overcomplicated решение. Проще вряд ли получится.
5 сен 13, 19:30    [14801675]     Ответить | Цитировать Сообщить модератору
 Re: Аналог TRY_CAST в 2008?  [new]
vino
Member

Откуда:
Сообщений: 1191
То есть, кроме создания пользовательской функции других вариантов не будет?
5 сен 13, 19:31    [14801678]     Ответить | Цитировать Сообщить модератору
 Re: Аналог TRY_CAST в 2008?  [new]
Гость333
Member

Откуда:
Сообщений: 3683
vino
То есть, кроме создания пользовательской функции других вариантов не будет?

Ну так ведь по приведённой ссылке нет никакой функции?
5 сен 13, 19:32    [14801681]     Ответить | Цитировать Сообщить модератору
 Re: Аналог TRY_CAST в 2008?  [new]
vino
Member

Откуда:
Сообщений: 1191
Гость333, помимо провала на денежных знаках она в некоторых случаях подходит (реплейсов можно добавить).
Но падение производительности, похоже, из-за Like ...
5 сен 13, 19:52    [14801735]     Ответить | Цитировать Сообщить модератору
 Re: Аналог TRY_CAST в 2008?  [new]
Гость333
Member

Откуда:
Сообщений: 3683
vino
она в некоторых случаях подходит

"Она" — это кто?
5 сен 13, 20:03    [14801753]     Ответить | Цитировать Сообщить модератору
 Re: Аналог TRY_CAST в 2008?  [new]
LexusR
Member

Откуда: Novosibirsk
Сообщений: 1887
МЫСЛЬ
5 сен 13, 20:04    [14801754]     Ответить | Цитировать Сообщить модератору
 Re: Аналог TRY_CAST в 2008?  [new]
vino
Member

Откуда:
Сообщений: 1191
Гость333, ее - конструкцию по предложенной ссылке - еще дополнять надо, так как при наличии пробелов между +- и числовым рядом провалится второй CAST. Например, дополнить так
CAST
 (
  CASE
   WHEN ISNUMERIC(Field)=1
    AND Field NOT LIKE '%[^0-9 +-]%'
    AND LEN(REPLACE(REPLACE(REPLACE(Field,' ',''),'-',''),'+',''))<=19
   THEN CASE WHEN CAST(REPLACE(Field,' ','') AS DEC(38,0)) BETWEEN -9223372036854775808 AND 9223372036854775807 THEN REPLACE(Field,' ','') END
  END AS BIGINT
 )

Согласен, это быстрее, чем пользовательскую функцию вызывать. Лучше варианта, я так понял, не будет...7
6 сен 13, 12:33    [14803824]     Ответить | Цитировать Сообщить модератору
 Re: Аналог TRY_CAST в 2008?  [new]
iap
Member

Откуда: Москва
Сообщений: 47142
vino
Гость333, ее - конструкцию по предложенной ссылке - еще дополнять надо, так как при наличии пробелов между +- и числовым рядом провалится второй CAST. Например, дополнить так
CAST
 (
  CASE
   WHEN ISNUMERIC(Field)=1
    AND Field NOT LIKE '%[^0-9 +-]%'
    AND LEN(REPLACE(REPLACE(REPLACE(Field,' ',''),'-',''),'+',''))<=19
   THEN CASE WHEN CAST(REPLACE(Field,' ','') AS DEC(38,0)) BETWEEN -9223372036854775808 AND 9223372036854775807 THEN REPLACE(Field,' ','') END
  END AS BIGINT
 )


Согласен, это быстрее, чем пользовательскую функцию вызывать. Лучше варианта, я так понял, не будет...7
Смотри-ка как интересно!
DEC(), оказывается не любит пробелы так, как любит их INT!
Спасибо!
6 сен 13, 14:48    [14804892]     Ответить | Цитировать Сообщить модератору
Все форумы / Microsoft SQL Server Ответить