How would I do pattern matching on this string in lua? - string
I have a string which contains a path to a file:
C:\Users\user\directory\build.bat
Is there a way I can remove the word between the last backslash and the second last backslash (in this case it is directory), however I would like a way to do this several times:
First time I run the code the path should look like this:
C:\Users\user\build.bat
If I run the code on the new string I just got from running the program the first time, the output should be like this:
C:\Users\build.bat
Yes, this is very much possible. I propose the following pattern:
^(.+)\.-\(.-)$ - this will match the entire path, matching first the directories up to the parent directory and then the filename. Use it as follows:
local function strip_parent_dir(path)
local path_to_parent, filename = path:match[[^(.+)\.-\(.-)$]]
return path_to_parent .. "\\" .. filename
end
which can then be used as follows:
print(strip_parent_dir[[C:\Users\user\directory\build.bat]]) -- C:\Users\user\build.bat
print(strip_parent_dir(strip_parent_dir[[C:\Users\user\directory\build.bat]])) -- C:\Users\build.bat
another option would be to split the path by the path delimiter (backslash), inserting the parts into a table, then removing the penultimate entry, finally concatenating the parts; this is slightly longer but may be considered more readable (and it may have better asymptotic performance):
local function strip_parent_dir(path)
local parts = {}
for part in path:gmatch"[^\\]+" do
table.insert(parts, part)
end
table.remove(parts, #parts - 1)
return table.concat(parts, "\\")
end
the results are the same. Choose whatever you consider more readable.
Related
Groovy replaceAll replacing multiple half matched strings
Working on a script where a user provides a file (yaml/json/txt) which has some string-formats to be replaced.These string formats can occur at any index. The problem I'm facing is that replaceAll is replacing multiple half-matched strings. Example: def secretfile = "This is first secret.adminlogin and then comes secret.adminloginpassword"; println(secretfile.replaceAll("secret.adminlogin", "root")); This is resulting in "This is first root and then comes rootpassword" . Where as the expected result is "This is first root and then comes secret.adminloginpassword" How can we make groovy replaceAll to only look for exact match of string. P.S , I cannot use split + replace + concatenation as the file can be a yaml/json and it might break it's linting.
Lua - Get first occurrance of substring using a pattern
I have a string that looks like: local str = "rootFolder\\<subFolder>\\<...>\\nFolder\\fileName"; where <...> could be a list of other folder names making the path/string very long. Also, I do not know what <subFolder> will actually be called since the folder name could be anything, i.e: rootFolder\\folderA\\... rootFolder\\folderB\\... rootFolder\\folderC\\... ... We can assume I know the name of the root folder because this will be known at runtime, so for now lets assume it is called rootFolder. How can I extract the sub-string <subFolder> using a pattern to match against str? I was thinking of something like: string.match(str, "rootFolder\\(.*)\\.*"); to capture the first folderName under rootFolder in the folder/directory hierarchy and ignore anything else that follows it but this is not working because, although it does match, it also gets everything else that follows it and not just the part I need (I also tried using .+ instead of .*). For example, I want to be able to do this: local str = "rootFolder\\hello\\anotherFolder\\myFile"; -- this pattern does not work as expected: local folderName = string.match(str, "rootFolder\\(.*)\\.*"); print(folderName == "hello"); -- true Hope that makes sense. Thank you.
The answer was to use a minus: local folderName = string.match(str, "rootFolder\\(.-)\\");
Go how can i efficient split string into parts
i am fighting with a string splitting. I want to split string by wildcards into a slice, but this slice should contain this wildcards as well. For example: /applications/{name}/tokens/{name} should be split into [/applications/ {name} /tokens/ {name}] etc. Here is a sample code i wrote, but it is not working correctly, and i don't feel good about it either. https://play.golang.org/p/VMOsJeaI4l There are some example routes to be tested. Method splitPath split path into parts and display both: before and after.
Here is a solution: var validPathRe = regexp.MustCompile("^(/{[[:alpha:]]+}|/[-_.[:alnum:]]+)+$") var splitPathRe = regexp.MustCompile("({[[:alpha:]]+}|[-_.[:alnum:]]+)") func splitPath(path string) parts{ var retPaths parts if !validPathRe.MatchString(path) { return retPaths } retPaths = splitPathRe.FindAllString(path, -1) return retPaths } I made this by creating two regular expressions, one to check if the path was valid or not, the other to extract the various parts of the path and return them. If the path is not valid it will return an empty list. The return of this will look like this: splitPath("/path/{to}/your/file.txt") ["path" "{to}" "your" "file.txt"] This doesn't include the '/' character because you already know that all strings in the return but the last string is a directory and the last string is the file name. Because of the validity check you can assume this.
splitting directory fileparts into sections using matlab / octave
I would like to split pathstr into separate parts how can I do this? See example below. PS: I'm using octave 3.8.1 dpath='tmp/h1/cli/pls/03sox_a_Fs_1000/' [pathstr,name,ext] = fileparts(dpath) >>>pathstr = tmp/h1/cli/pls/03sox_a_Fs_1000 If all I want is 03sox_a_Fs_1000 or pls How can I do this? Please note the filenames will change and could be of different lengths.
You can use strsplit (here using Matlab) to split your string (believe it or not!) using the delimiter /: pathstr = 'tmp/h1/cli/pls/03sox_a_Fs_1000' [Name,~] = strsplit(pathstr,'/') Now Name looks like this: Name = 'tmp' 'h1' 'cli' 'pls' '03sox_a_Fs_1000' So you can select the last element using the end keyword and curly braces since the output of strsplit is a cell array: Name = Name{end} or end-1 to retrieve pls. This applies to names of any length or format, as long as they are separated by /.
Lua: Search a specific string
Hi all tried all the string pattrens and library arguments but still stuck. i want to get the name of the director from the following string i have tried the string.matcH but it matches the from the first character it finD from the string the string is... fixstrdirector = {id:39254,cast:[{id:15250,name:Hope Davis,character:Aunt Debra,order:5,cast_id:10,profile_path:/aIHF11Ss8P0A8JUfiWf8OHPVhOs.jpg},{id:53650,name:Anthony Mackie,character:Finn,order:3,cast_id:11,profile_path:/5VGGJ0Co8SC94iiedWb2o3C36T.jpg},{id:19034,name:Evangeline Lilly,character:Bailey Tallet,order:2,cast_id:12,profile_path:/oAOpJKgKEdW49jXrjvUcPcEQJb3.jpg},{id:6968,name:Hugh Jackman,character:Charlie Kenton,order:0,cast_id:13,profile_path:/wnl7esRbP3paALKn4bCr0k8qaFu.jpg},{id:79072,name:Kevin Durand,character:Ricky,order:4,cast_id:14,profile_path:/c95tTUjx5T0D0ROqTcINojpH6nB.jpg},{id:234479,name:Dakota Goyo,character:Max Kenton,order:1,cast_id:15,profile_path:/7PU6n4fhDuFwuwcYVyRNVEZE7ct.jpg},{id:8986,name:James Rebhorn,character:Marvin,order:6,cast_id:16,profile_path:/ezETMv0YM0Rg6YhKpu4vHuIY37D.jpg},{id:930729,name:Marco Ruggeri,character:Cliff,order:7,cast_id:17,profile_path:/1Ox63ukTd2yfOf1LVJOMXwmeQjO.jpg},{id:19860,name:Karl Yune,character:Tak Mashido,order:8,cast_id:18,profile_path:/qK315vPObCNdywdRN66971FtFez.jpg},{id:111206,name:Olga Fonda,character:Farra Lemkova,order:9,cast_id:19,profile_path:/j1qabOHf3Pf82f1lFpUmdF5XvSp.jpg},{id:53176,name:John Gatins,character:Kingpin,order:10,cast_id:41,profile_path:/A2MqnSKVzOuBf8MVfNyve2h2LxJ.jpg},{id:1126350,name:Sophie Levy,character:Big Sister,order:11,cast_id:42,profile_path:null},{id:1126351,name:Tess Levy,character:Little Sister,order:12,cast_id:43,profile_path:null},{id:1126352,name:Charlie Levy,character:Littlest Sister,order:13,cast_id:44,profile_path:null},{id:187983,name:Gregory Sims,character:Bill Panner,order:14,cast_id:45,profile_path:null}],crew:[{id:58726,name:Leslie Bohem,department:Writing,job:Screenplay,profile_path:null},{id:53176,name:John Gatins,department:Writing,job:Screenplay,profile_path:/A2MqnSKVzOuBf8MVfNyve2h2LxJ.jpg},{id:17825,name:Shawn Levy,department:Directing,job:Director,profile_path:/7f2f8EXdlWsPYN0HPGcIlG21xU.jpg},{id:12415,name:Richard Matheson,department:Writing,job:Story,profile_path:null},{id:57113,name:Dan Gilroy,department:Writing,job:Story,profile_path:null},{id:25210,name:Jeremy Leven,department:Writing,job:Story,profile_path:null},{id:17825,name:Shawn Levy,department:Production,job:Producer,profile_path:/7f2f8EXdlWsPYN0HPGcIlG21xU.jpg},{id:34970,name:Susan Montford,department:Production,job:Producer,profile_path:/1XJt51Y9ciPhkHrAYE0j6Jsmgji.jpg},{id:3183,name:Don Murphy,department:Production,job:Producer,profile_path:null},{id:34967,name:Rick Benattar,department:Production,job:Producer,profile_path:null},{id:1126348,name:Eric Hedayat,department:Production,job:Producer,profile_path:null},{id:186721,name:Ron Ames,department:Production,job:Producer,profile_path:null},{id:10956,name:Josh McLaglen,department:Production,job:Executive Producer,profile_path:null},{id:57634,name:Mary McLaglen,department:Production,job:Executive Producer,profile_path:null},{id:23779,name:Jack Rapke,department:Production,job:Executive Producer,profile_path:null},{id:488,name:Steven Spielberg,department:Production,job:Executive Producer,profile_path:/cuIYdFbEe89PHpoiOS9tmo84ED2.jpg},{id:30,name:Steve Starkey,department:Production,job:Executive Producer,profile_path:null},{id:24,name:Robert Zemeckis,department:Production,job:Executive Producer,profile_path:/isCuZ9PWIOyXzdf3ihodXzjIumL.jpg},{id:531,name:Danny Elfman,department:Sound,job:Original Music Composer,profile_path:/pWacZpYPos8io22nEiim7d3wp2j.jpg},{id:18265,name:Mauro Fiore,department:Crew,job:Cinematography,profile_path:null},{id:54271,name:Dean Zimmerman,department:Editing,job:Editor,profile_path:null},{id:25365,name:Richard Hicks,department:Production,job:Casting,profile_path:null},{id:5490,name:David Rubin,department:Production,job:Casting,profile_path:null},{id:52088,name:Tom Meyer,department:Art,job:Production Design,profile_path:null}]} i have tried string.match(fixstrdirector,"name:(.+),department:Directing") but it gives me the from the first occurace it find the name to the end of thr string output: Hope Davis,character:Aunt Debra,order:5,cast_id:10,profile_path:/aIHF11Ss8P0A8JUfiWf8OHPVhOs.jpg},{id:53650,name:Anthony Mackie,character:Finn,order:3,cast_id:11,profile_path:/5VGGJ0Co8SC94iiedWb2o3C36T.jpg},{id:19034,name:Evangeline Lilly,character:Bailey Tallet,order:2,cast_id:12,profile_path:/oAOpJKgKEdW49jXrjvUcPcEQJb3.jpg},{id:6968,name:Hugh Jackman,character:Charlie Kenton,order:0,cast_id:13,profile_path:/wnl7esRbP3paALKn4bCr0k8qaFu.jpg},{id:79072,name:Kevin Durand,character:Ricky,order:4,cast_id:14,profile_path:/c95tTUjx5T0D0ROqTcINojpH6nB.jpg},{id:234479,name:Dakota Goyo,character:Max Kenton,order:1,cast_id:15,profile_path:/7PU6n4fhDuFwuwcYVyRNVEZE7ct.jpg},{id:8986,name:James Rebhorn,character:Marvin,order:6,cast_id:16,profile_path:/ezETMv0YM0Rg6YhKpu4vHuIY37D.jpg},{id:930729,name:Marco Ruggeri,character:Cliff,order:7,cast_id:17,profile_path:/1Ox63ukTd2yfOf1LVJOMXwmeQjO.jpg},{id:19860,name:Karl Yune,character:Tak Mashido,order:8,cast_id:18,profile_path:/qK315vPObCNdywdRN66971FtFez.jpg},{id:111206,name:Olga Fonda,character:Farra Lemkova,order:9,cast_id:19,profile_path:/j1qabOHf3Pf82f1lFpUmdF5XvSp.jpg},{id:53176,name:John Gatins,character:Kingpin,order:10,cast_id:41,profile_path:/A2MqnSKVzOuBf8MVfNyve2h2LxJ.jpg},{id:1126350,name:Sophie Levy,character:Big Sister,order:11,cast_id:42,profile_path:null},{id:1126351,name:Tess Levy,character:Little Sister,order:12,cast_id:43,profile_path:null},{id:1126352,name:Charlie Levy,character:Littlest Sister,order:13,cast_id:44,profile_path:null},{id:187983,name:Gregory Sims,character:Bill Panner,order:14,cast_id:45,profile_path:null}],crew:[{id:58726,name:Leslie Bohem,department:Writing,job:Screenplay,profile_path:null},{id:53176,name:John Gatins,department:Writing,job:Screenplay,profile_path:/A2MqnSKVzOuBf8MVfNyve2h2LxJ.jpg},{id:17825,name:Shawn Levy
You're searching from the first occurrence of "name:" until the "department:Directing" with everything in between. Instead, you need to restrict what can be between the two strings. Here for example I'm saying that the characters that make up the name can only be alphanumeric or a space: string.match(fixstrdirector,"name:([%w ]+),department:Directing") Alternatively, given that there's a comma separating the parameters, a better approach would be to search for "name:" followed by any characters other than a comma, followed by "department:Directing": string.match(fixstrdirector,"name:([^,]+),department:Directing") Of course that wouldn't work if the name had a comma it in!
Lua patterns provides - modifier for tasks as you have above. As stated on PiL - Section 20.2: The + modifier matches one or more characters of the original class. It will always get the longest sequence that matches the pattern. Like *, the modifier - also matches zero or more occurrences of characters of the original class. However, instead of matching the longest sequence, it matches the shortest one. Next, when you are using . to match, it'll find any and all characters satisfying the pattern. Therefore, you'll get the result from first occurence of name until the ,department:Directing is found. Since you know that it is a JSON data, you can try to match for [^,]; that is, non-comma characters. So, for your case try: local tAllNames = {} for sName in fixstrdirector:gmatch( "name:([^,]-),department:Directing" ) do tAllNames[ #tAllNames + 1 ] = sName end and all your required names will be stored in the table tAllNames. An example of the above can be seen at codepad.