1

I'm trying to figure out a way, so far unsuccessfully, to add a new line ("\n") to a very long string.

Is there a function that will insert a new line every x amount of characters? Basically, I need to add a newline every 95 characters. Here's the text I'm working with:

MEMORANDUM FOR RECORD

SUBJECT: Subject

1) Nam fabulas mnesarchum comprehensam ne, cu ullum euismod consulatu usu. Eam alii lobortis voluptatum id, denique eligendi pertinax quo ne. Vis congue eirmod ut. Duo probo soleat ex. Elit pertinax abhorreant eu his, ipsum dicam dissentiunt pri id. Kasd erant dolorum id sed, ei vim partem deseruisse, ne mea dico tantas alienum.

2) Has cu facilisis mediocritatem. Fabellas lucilius vim ex. Mei simul omnium et, wisi vidit ut ius. Ad has erat honestatis. Malis animal aliquid id usu.

3) Nulla utinam appellantur cu qui, scripta sententiae disputando eu nam, ut pri unum labore. Odio wisi torquatos sea cu. Ut detracto torquatos repudiandae pri. Vim puto solum epicurei at. Per nonummy perpetua similique te, odio platonem ut pri. Mei indoctum prodesset in, eam nisl quaerendum at.

4) At vero eos et accusamus et iusto odio dignissimos ducimus qui blanditiis praesentium voluptatum deleniti atque corrupti quos dolores et quas molestias excepturi sint occaecati cupiditate non provident, similique sunt in culpa qui officia deserunt mollitia animi, id est laborum et dolorum fuga. Et harum quidem rerum facilis est et expedita distinctio. Nam libero tempore, cum soluta nobis est eligendi optio cumque nihil impedit quo minus id quod maxime placeat facere possimus, omnis voluptas assumenda est, omnis dolor repellendus.

4 Answers 4

2

I'm interpreting the question as: I want to divide the text into lines of at most, but as close as possible to 95 characters, breaking on whitespace.

I'm ignoring the file IO in the other answers. Here goes:

-- Second parameter governs where to break; defaults to 80.
-- Call me like: breakAt(longstring, 95)
local function breakAt(str, lineLength)
    local lineLength = lineLength or 80
    -- Arrays are more efficient for large text operations.
    local out = {}
    -- Match line without newlines; save original newlines.
    for line, breaks in str:gmatch('([^\n]+)(\n+)') do
        local count = 0
        -- Match whitespace with '*' to allow for the last word on the line having no adjacent whitespace.
        for word, whitespace in line:gmatch('(%S+)(%s*)') do
            count = count + #word
            if count > lineLength then
                -- If this word crosses the lineLength boundary, replace the last words' whitespace with a newline.
                out[#out] = '\n'
                -- The current word is the first on the new line.
                count = #word
            end
            count = count + #whitespace
            table.insert(out, word)
            table.insert(out, whitespace)
        end
        table.insert(out, breaks)
    end
    return table.concat(out)
end

This'll break the string on the whitespace, maximizing the number of words on a line.

Sign up to request clarification or add additional context in comments.

1 Comment

Keyword break cannot be used as function name in Lua.
1

It's easy!

local text = io.open'memorandum.txt':read'*a'  -- Load text from file
local n0, width = 0, 80
text = text:gsub('()(%s)',
    function(n, c)
        c = (n-n0 > width) and '\n' or c
        n0 = (c == '\n') and n or n0
        return c
    end)
io.open('memorandum2.txt','w'):write(text)  -- Save corrected text to file

3 Comments

You can add :close() to the last line.
@lhf - Unfortunatelly, it works in Lua 5.2 only. File will be auto closed on program exit anyway.
You should return nil or false, so no replacement is done if you don't have to, but good answer otherwise of course (+1) :)
0

Try print(s:gsub("("..string.rep(".",95)..")","%1\n")).

But I suspect you want to do this for each line, not for the whole text.

Comments

0

This will directly output any lines shorter than 95 characters, and split lines 95+ characters into 94 character chunks with a newline appended. it doesn't split on white-space, that is left as an exercise to you.

local fout = io.output(os.getenv('userprofile').. '\\desktop\\temp.txt', 'w+');
for str in string.gmatch(text, '(.-\n)') do
    if str:len() > 95 then
        while str:len() > 95 do
            local s = str:sub(1, 94)
            fout:write(s.. '\n')
            str = str:sub(94)
        end
    else
        fout:write(str)
    end
end
fout:flush(); fout:close();

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.