Split a string by \n or \r using string.gmatch()
Asked Answered
M

3

9

A simple pattern should do the job but I can't come up with/find something that works. I am looking to have something like this:

lines = string.gmatch(string, "^\r\n") 
Middlebuster answered 29/9, 2015 at 14:48 Comment(0)
S
24

To split a string into table (array) you can use something like this:

str = "qwe\nasd\rzxc"
lines = {}
for s in str:gmatch("[^\r\n]+") do
    table.insert(lines, s)
end
Steiger answered 29/9, 2015 at 15:9 Comment(1)
This does not work on "hello\n\nworld": the result should be three strings, one of which is the empty string.Puritanical
I
6

An important point - solutions which use gmatch to drop the delimiter do NOT match empty strings between two newlines, so if you want to preserve these like a normal split implementation (for example, to compare lines across two documents) you are better off matching the delimiter such as in this example:

function string:split(delimiter)
  local result = { }
  local from  = 1
  local delim_from, delim_to = string.find( self, delimiter, from  )
  while delim_from do
    table.insert( result, string.sub( self, from , delim_from-1 ) )
    from  = delim_to + 1
    delim_from, delim_to = string.find( self, delimiter, from  )
  end
  table.insert( result, string.sub( self, from  ) )
  return result
end

Credit to https://gist.github.com/jaredallard/ddb152179831dd23b230.

Inflight answered 17/8, 2018 at 10:41 Comment(0)
M
2

I found the answer: use "[^\r\n]+" ('+' is for skipping over empty lines).

Before, I was purposely avoiding using brackets because I thought that it indicates a special string literal that doesn't support escaping. Well, that was incorrect. It is double brackets that do that.
Lua string.gsub() by '%s' or '\n' pattern

Middlebuster answered 29/9, 2015 at 15:6 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.