0

I'm looking for a way to achieve replacements in a string.

Let's say I have a text which is (([343]+([509])*[1584]))/25. I want each number that exists in this text (which is enclosed in brackets) be updated with a value plus 2000.

So, this (([343]+([509])*[1584]))/25 should become this (([2343]+([2509])*[3584]))/25

I should do this via MS SQL. Could anyone get me started?

4
  • 8
    "plus 2000" is not a replace Commented Jun 6, 2016 at 13:41
  • 5
    This kind of thing is better to do in a programming language then in t-sql. A pure t-sql solution is possible, but it will be a cumbersome code and not very efficient. Commented Jun 6, 2016 at 13:43
  • 4
    If you have to do it "via MS Sql", this might be a good time to use CLR. Commented Jun 6, 2016 at 13:47
  • So, any of the answers helps you? Commented Jun 7, 2016 at 14:06

3 Answers 3

3
DECLARE @val VARCHAR(100) = '(([343]+([509])*[1584]))/25', 
        @xml xml

SELECT @xml = CAST('<a>'+REPLACE(REPLACE(@val,']','</a><a>'),'[','</a><a>')+'</a>' as xml)

SELECT @val = CAST ((
SELECT CASE WHEN try_cast(t.v.value('.','nvarchar(max)') as int) is not null 
            THEN QUOTENAME(try_cast(t.v.value('.','nvarchar(max)') as int)+2000) 
            ELSE t.v.value('.','nvarchar(max)') END
FROM @xml.nodes('/a') as t(v)
FOR XML PATH('')) as nvarchar(max))

SELECT @val

Output:

(([2343]+([2509])*[3584]))/25
Sign up to request clarification or add additional context in comments.

Comments

2
DECLARE @val VARCHAR(100) = '(([343]+([509])*[1584]))/25'

SELECT STUFF((
SELECT '[' + ISNULL(REPLACE(val, token, token + 2000), val)
FROM (
    SELECT token = PARSENAME(REPLACE(t.val, ']', '.'), 2), *
    FROM (
        SELECT val = t.c.value('(./text())[1]', 'VARCHAR(100)')
        FROM ( 
            SELECT x = CONVERT(XML, '<i>' + REPLACE(@val, '[', '</i><i>') + '</i>').query('.')
        ) a
        CROSS APPLY x.nodes('i') t(c)
    ) t
) t
FOR XML PATH(''), TYPE).value('.', 'NVARCHAR(MAX)'), 1, 1, '')

1 Comment

I would use varchar(max) just in case, to avoid a truncated string
0

An alternative using a user defined scalar function:

CREATE FUNCTION [dbo].[fnReplaceNumbers]
(
    @string varchar(max),
    @valueToAdd int
)
RETURNS NVARCHAR(MAX)
AS
BEGIN
    declare @i int
    declare @len int
    declare @char varchar(1);
    declare @inToken bit;
    declare @num varchar(32);
    declare @result varchar(max);

    set @i = 1
    set @len = LEN(@string);
    set @inToken = 0;
    set @num = '';
    set @result = '';

    declare @table table(x varchar(128));


    WHILE @i <= @len
    BEGIN
        set @char = SUBSTRING(@string, @i, 1);

        if (@char = ']') set @inToken = 0;

        if (@inToken = 1) begin
            set @num = @num + @char;
        end else if (@inToken = 0) begin
            if (len(@num) > 0) begin
                set @result = @result + cast((cast(@num as int) + @valueToAdd) as varchar(max));
                set @num = '';
            end;
            set @result = @result + @char;
        end;

        if (@char = '[') set @inToken = 1;


        set @i = @i + 1;
    END

    return @result;
END

..and then just call it as follows:

select dbo.fnReplaceNumbers('(([343]+([509])*[1584]))/25', 2000)

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.