Удалить последний символ в строке в T-SQL?


142

Как удалить последний символ в строке T-SQL?

Например:

'TEST STRING'

возвращаться:

'TEST STRIN'

Ответы:


197

например

DECLARE @String VARCHAR(100)
SET @String = 'TEST STRING'

-- Chop off the end character
SET @String = 
     CASE @String WHEN null THEN null 
     ELSE (
         CASE LEN(@String) WHEN 0 THEN @String 
            ELSE LEFT(@String, LEN(@String) - 1) 
         END 
     ) END


SELECT @String

72
В качестве альтернативы: ВЫБРАТЬ ВЛЕВО (YourColumnName, LEN (YourColumnName) - 1) ОТ YourTable
— Кайл Б.

3
Спасибо за нулевой улов - ISNULL (LEFT (@String, LEN (@String) - 1), 'ErrMsg') решит
— Volvox

2
@Volvox все равно будет генерировать исключение, если строка пустая, я изменяю ваш ответ для обработки этого сценария.
— Имран Ризви,

108

Если по какой-то причине ваша логика столбца сложна (случай, когда ... then ... else ... end), то приведенные выше решения заставят вас повторить ту же логику в функции len (). Дублирование одной и той же логики превращается в беспорядок. Если это так, то стоит обратить внимание на это решение. Этот пример избавляется от последней нежелательной запятой. Наконец-то я нашел применение функции REVERSE.

select reverse(stuff(reverse('a,b,c,d,'), 1, 1, ''))

6
Обратите внимание, что этот код возвращается, NULLесли передана строка, которая короче диапазона удаления, указанного для STUFF. Оберните его в, ISNULLчтобы получить другое выходное значение для случая пустой строки.
— Rozwel

12
Приятно использовать это с внешним применением, с путем для xml (''), чтобы исключить запятую в конце. awseome
— Tracker1

Точно так же, как @ Tracker1. В отличие от всего, что связано с LEN (), это изящно работает (без каких-либо повторений) для пустой строки (особенно заключенной в ISNULL ())
— gregmac 04

Удивительно, насколько жестоким иногда может быть SQL. Это невероятно.
— eouw0o83hf 01

Спасибо, это помогло мне, в моем случае у меня был последний пробел, поэтому первый индекс - 2select reverse(stuff(reverse('a,b,c,d,'), 2, 1, ''))
— Arngue

55

Попробуй это:

select substring('test string', 1, (len('test string') - 1))

@Adrien есть идеи, почему это дает тот же результат, что и select substring('test string', 0, len('test string'))?
— Луи Ваверу

@Louis, синтаксис подстрока выглядит следующим образом : SUBSTRING ( expression ,start , length ). Теперь оба запроса возвращают то же самое, потому что нумерация основана на 1, что означает, что первый символ в выражении равен 1. Если start меньше 1, возвращаемое выражение начнется с первого символа, указанного в выражении. Источник
— JS5

26

Если ваша строка пуста,

DECLARE @String VARCHAR(100)
SET @String = ''
SELECT LEFT(@String, LEN(@String) - 1)

тогда этот код вызовет сообщение об ошибке «Неверный параметр длины передан функции подстроки».

Вы можете справиться с этим следующим образом:

SELECT LEFT(@String, NULLIF(LEN(@String)-1,-1))

Он всегда будет возвращать результат, а в случае пустой строки - NULL.


12

Это будет работать, даже если исходный текст / var равен нулю или пуст:

SELECT REVERSE(SUBSTRING(REVERSE(@a), 2, 9999))

2
Это недооцененный комментарий, он быстрый, и для работы не нужно дважды выбирать строку.
— Randall


7

Если ваш столбец есть, textа нет varchar, вы можете использовать это:

SELECT SUBSTRING(@String, 1, NULLIF(DATALENGTH(@String)-1,-1))

6

Если вы хотите сделать это за два шага, а не за три из REVERSE-STUFF-REVERSE, вы можете сделать разделитель списка одним или двумя пробелами. Затем используйте RTRIM, чтобы обрезать конечные пробелы, и REPLACE, чтобы заменить двойные пробелы на ','

select REPLACE(RTRIM('a  b  c  d  '),'  ', ', ')

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

Не уверен в производительности. Каждый REVERSE создает новую копию строки, но STUFF на треть быстрее, чем REPLACE.

также см. это




2

вы можете создать функцию

CREATE FUNCTION [dbo].[TRUNCRIGHT] (@string NVARCHAR(max), @len int = 1)
RETURNS NVARCHAR(max)
AS
BEGIN
    IF LEN(@string)<@len
        RETURN ''
    RETURN LEFT(@string, LEN(@string) - @len)
END


2

Получить последнего персонажа

Right(@string, len(@String) - (len(@String) - 1))

Я не думаю, что это то, о чем он спрашивал, однако, это может быть полезно добавить в комментарий.
— jimwise

3
Правильно (@string, 1).
— GoalBased

2

Это довольно поздно, но, что интересно, еще никогда не упоминалось.

select stuff(x,len(x),1,'')

то есть:

take a string x
go to its last character
remove one character
add nothing

1

Мой ответ похож на принятый ответ, но он также проверяет наличие Null и Empty String.

DECLARE @String VARCHAR(100)

SET @String = 'asdfsdf1'

-- If string is null return null, else if string is empty return as it is, else chop off the end character
SET @String = Case @String when null then null else (case LEN(@String) when 0 then @String else LEFT(@String, LEN(@String) - 1) end ) end

SELECT @String

0

Мне нравится ответ @Bill-Hoenig; однако я использовал подзапрос, и меня догнали, потому что функция REVERSE требовала двух наборов круглых скобок. Мне потребовалось время, чтобы понять это!

SELECT
   -- Return comma delimited list of all payment reasons for this Visit
   REVERSE(STUFF(REVERSE((
        SELECT DISTINCT
               CAST(CONVERT(varchar, r1.CodeID) + ' - ' + c.Name + ', ' AS VARCHAR(MAX))
          FROM VisitReason r1
          LEFT JOIN ReasonCode c        ON c.ID = r1.ReasonCodeID
         WHERE p.ID = r1.PaymentID
         FOR XML PATH('')
              )), 1, 2, ''))                        ReasonCode
  FROM Payments p

Вы можете использовать внешнее / перекрестное применение для составной части запроса. Я использую это, чтобы получить набор флагов для родительского элемента.
— Tracker1 04

0

Чтобы обновить запись путем обрезки последних N символов определенного столбца:

UPDATE tablename SET columnName = LEFT(columnName , LEN(columnName )-N) where clause


0
declare @string varchar(20)= 'TEST STRING'
Select left(@string, len(@string)-1) as Tada

выход:

Tada
--------------------
TEST STRIN

0

Попробуй это,

DECLARE @name NVARCHAR(MAX) SET @name='xxxxTHAMIZHMANI****'SELECT Substring(@name, 5, (len(@name)-8)) as UserNames

И на выходе будет THAMIZHMANI


-1
declare @x varchar(20),@y varchar(20)
select @x='sam'
select 
case when @x is null then @y
      when @y is null then @x
      else @x+','+@y
end


go

declare @x varchar(20),@y varchar(20)
select @x='sam'
--,@y='john'
DECLARE @listStr VARCHAR(MAX)   

SELECT @listStr = COALESCE(@x + ', ' ,'') +coalesce(@y+',','')
SELECT left(@listStr,len(@listStr)-1)
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.