4

I have a text like: Sentence one. Sentence two. Sentence three.

I want it to be:

  • Sentence one.
  • Sentence two.
  • Sentence three.

I assume I can replace '.' with '.' + char(10) + char(13), but how can I go about bullets? '•' character works fine if printed manually I just do not know how to bullet every sentence including the first.

user194076
  • 8,787
  • 23
  • 94
  • 154

3 Answers3

4
-- Initial string
declare @text varchar(100)
set @text = 'Sentence one. Sentence two. Sentence three.'

-- Setting up replacement text - new lines (assuming this works) and bullets ( char(149) )
declare @replacement varchar(100)
set @replacement = '.' + char(10) + char(13) + char(149)

-- Adding a bullet at the beginning and doing the replacement, but this will also add a trailing bullet
declare @processedText varchar(100)
set @processedText = char(149) + ' ' + replace(@text, '.', @replacement)

-- Figure out length of substring to select in the next step
declare @substringLength int
set @substringLength = LEN(@processedText) - CHARINDEX(char(149), REVERSE(@processedText))

-- Removes trailing bullet
select substring(@processedText, 0, @substringLength)

I've tested here - https://data.stackexchange.com/stackoverflow/qt/119364/

I should point out that doing this in T-SQL doesn't seem correct. T-SQL is meant to process data; any presentation-specific work should be done in the code that calls this T-SQL (C# or whatever you're using).

Community
  • 1
  • 1
Jeremy Wiggins
  • 7,239
  • 6
  • 41
  • 56
  • 1
    In SSMS, when you send results to grid (default output), newlines don't have any effect. If you send results to text (ctrl-T), then you'll see your newlines correctly displayed. Only thing I'd point out is that you have a space between bullets on lines 2/3 but none on line 1. – billinkc Nov 28 '11 at 02:37
  • Oh cool, I didn't know that. Good catch on the space as well. Query & link have been updated appropriately, ty. – Jeremy Wiggins Nov 28 '11 at 02:58
1

Here's my over-the-top approach but I feel it's a fairly solid approach. It combines classic SQL problem solving techniques of Number tables for string slitting and use of the FOR XML for concatenating the split lines back together. The code is long but the only place you'd need to actually edit is the SOURCE_DATA section.

No knock on @Jeremy Wiggins approach, but I prefer mine as it lends itself well to a set based approach in addition to being fairly efficient code.

-- This code will rip lines apart based on @delimiter
-- and put them back together based on @rebind
DECLARE 
    @delimiter char(1)
,   @rebind varchar(10);

SELECT
    @delimiter = '.'
,   @rebind = char(10) + char(149) + ' ';

;
-- L0 to L5 simulate a numbers table
-- http://billfellows.blogspot.com/2009/11/fast-number-generator.html
WITH L0 AS
(
    SELECT
        0 AS C
    UNION ALL
    SELECT
        0
)
, L1 AS
(
    SELECT
        0 AS c
    FROM
        L0 AS A
        CROSS JOIN L0 AS B
)
, L2 AS
(
    SELECT
        0 AS c
    FROM
        L1 AS A
        CROSS JOIN L1 AS B
)
, L3 AS
(
    SELECT
        0 AS c
    FROM
        L2 AS A
        CROSS JOIN L2 AS B
)
, L4 AS
(
    SELECT
        0 AS c
    FROM
        L3 AS A
        CROSS JOIN L3 AS B
)
, L5 AS
(
    SELECT
        0 AS c
    FROM
        L4 AS A
        CROSS JOIN L4 AS B
)
, NUMS AS
(
    SELECT
        ROW_NUMBER() OVER (ORDER BY (SELECT NULL)) AS number
    FROM
        L5
)
, SOURCE_DATA (ID, content) AS
(
    -- This query simulates your input data
    SELECT 1, 'Sentence one. Sentence two. Sentence three.'
    UNION ALL SELECT 7, 'In seed time learn, in harvest teach, in winter enjoy.Drive your cart and your plow over the bones of the dead.The road of excess leads to the palace of wisdom.Prudence is a rich, ugly old maid courted by Incapacity.He who desires but acts not, breeds pestilence.'
)
, MAX_LENGTH AS
(
    -- this query is rather important. The current NUMS query generates a 
    -- very large set of numbers but we only need 1 to maximum lenth of our
    -- source data. We can take advantage of a 2008 feature of letting
    -- TOP take a dynamic value
    SELECT TOP (SELECT MAX(LEN(SD.content)) AS max_length FROM SOURCE_DATA SD)
        N.number
    FROM
        NUMS N
)
, MULTI_LINES AS
(
    -- This query will make many lines out a single line based on the supplied delimiter
    -- Need to retain the ID (or some unique value from original data to regroup it
    -- http://www.sommarskog.se/arrays-in-sql-2005.html#tblnum
    SELECT 
        SD.ID
    ,   LTRIM(substring(SD.content, Number, charindex(@delimiter, SD.content + @delimiter, Number) - Number)) + @delimiter AS lines
    FROM
        MAX_LENGTH
        CROSS APPLY
            SOURCE_DATA SD
    WHERE
        Number <= len(SD.content)
        AND substring(@delimiter + SD.content, Number, 1) = @delimiter
)
, RECONSITITUE (content, ID) AS
(
    -- use classic concatenation to put it all back together
    -- using CR/LF * (space) as delimiter
    -- as a correlated sub query and joined back to our original table to preserve IDs
    -- https://stackoverflow.com/questions/5196371/sql-query-concatenating-results-into-one-string
    SELECT DISTINCT 
    STUFF
    ( 
        (
            SELECT @rebind + M.lines
            FROM MULTI_LINES M
            WHERE M.ID = ML.ID
            FOR XML PATH('')
        )
    , 1
    , 1
    , '')
    ,   ML.ID
    FROM 
        MULTI_LINES ML
)
SELECT 
    R.content
,   R.ID
FROM 
    RECONSITITUE R

Results

content                                                       ID
-----------------------------------------------------------   ---
• In seed time learn, in harvest teach, in winter enjoy.
• Drive your cart and your plow over the bones of the dead.
• The road of excess leads to the palace of wisdom.
• Prudence is a rich, ugly old maid courted by Incapacity.
• He who desires but acts not, breeds pestilence.             7
• Sentence one.
• Sentence two.
• Sentence three.                                             1

(2 row(s) affected)

References

Community
  • 1
  • 1
billinkc
  • 59,250
  • 9
  • 102
  • 159
  • Sorry for the late response. I never got a chance to test this thing, but now I did, and it works like a charm! Also, thanks for the links. Very informative. – user194076 Dec 21 '11 at 23:54
0

select '• On '+ cast(getdate() as varchar)+' I discovered how to do this '

Sample

  • As it’s currently written, your answer is unclear. Please [edit] to add additional details that will help others understand how this addresses the question asked. You can find more information on how to write good answers [in the help center](/help/how-to-ask). – Community Sep 22 '21 at 06:13