【问题标题】:Lua string.find() errorLua string.find() 错误
【发布时间】:2017-08-08 05:47:15
【问题描述】:

所以我正在编写一个 Lua 脚本并对其进行了测试,但出现了一个我不知道如何修复的错误:

.\search.lua:10: malformed pattern (missing ']')

下面是我的代码。如果你知道我做错了什么,如果你能告诉我会非常有帮助。

weird = "--[[".."\n"
function readAll(file)
    local c = io.open(file, "rb")
    local j = c:read("*all")
    c:close()
    return(j)
end
function blockActive()
    local fc = readAll("functions.lua")
    if string.find(fc,weird) ~= nil then
        require("blockDeactivated")
        return("false")
    else
        return("true")
    end
end
print(blockActive())

编辑:第一条评论有答案。我变了 weird = "--[[".."\n"weird = "%-%-%[%[".."\r" \n\r 的变化是因为它实际上本来应该是这样的。

【问题讨论】:

  • 解决方案#1:string.find(fc,weird,1,true),解决方案#2:weird = "%-%-%[%[".."\n"
  • 是的,这对我有用。我不得不将“\n”改为“\r”,但那是因为我一开始就做错了。

标签: lua


【解决方案1】:

此错误是因为 string.find 使用 Lua Patterns

大多数非字母数字字符,例如"[", ".", "-" 等都传达特殊含义。

string.find(fc,weird),或者更好,fc:find(weird) 正在尝试解析这些特殊字符,并出错。

不过,您可以使用这些模式来抵消其他模式。

weird = ("--[["):gsub("%W","%%%0") .. "\r?\n"

这有点令人生畏,但希望它是有意义的。

("--[[") 是你奇怪字符串的原始第一部分,按预期工作。

:gsub() 是一个用另一种模式替换模式的函数。再次,请参阅Patterns

"%W" 是一个匹配所有不是字母、数字或下划线的字符串的模式。

%%%0 替换与自己匹配的所有内容(%0 是一个字符串,表示此匹配中的所有内容),跟在 % 之后,它被转义了。

所以这意味着[[会变成%[%[,这就是如何查找,以及类似模式'转义'的特殊字符。

\n 现在是\r?\n 的原因是指这些模式。如果它以 \n 结尾,则匹配它,就像以前一样。但是,如果它在 Windows 上运行,则换行符可能看起来像 \r\n。 (您可以阅读此HERE)。 ? 跟在一个字符之后,在这种情况下是 \r,意味着它可以可选地匹配它。所以这匹配--[[\n--[[\r\n,同时支持windows和linux。

现在,当您运行 fc:find(weird) 时,它正在运行 fc:find("%-%-%[%[\r?\n"),这应该正是您想要的。

希望这有帮助!

如果你有点懒,完成代码

weird = ("--[["):gsub("%W","%%%0") .. "\r?\n" // Escape "--[[", add a newline. Used in our find.

// readAll(file)
// Takes a string as input representing a filename, returns the entire contents as a string.
function readAll(file)
    local c = io.open(file, "rb")   // Open the file specified by the argument. Read-only, binary (Doesn't autoformat things like \r\n)
    local j = c:read("*all")        // Dump the contents of the file into a string.
    c:close()                       // Close the file, free up memory.
    return j                        // Return the contents of the string.
end

// blockActive()
// returns whether or not the weird string was matched in 'functions.lua', executes 'blockDeactivated.lua' if it wasn't.
function blockActive()
    local fc = readAll("functions.lua") // Dump the contents of 'functions.lua' into a string.
    if fc:find(weird) then              // If it functions.lua has the block-er.
        require("blockDeactivated")     // Require (Thus, execute, consider loadfile instead) 'blockDeactived.lua'
        return false                    // Return false.
    else
        return true                     // Return true.
    end
end
print(blockActive()) // Test? the blockActve code.

【讨论】:

  • 检查我的问题的 cmets。谢谢,但我在一个多星期前找到了答案。
  • 。好吧,享受我的小事实填充文章。
  • 大声笑,它实际上对其他一些事情也很有帮助。我实际上不知道 Windows 如何将新行格式化为\r\n,这对我编写的几个新脚本有所帮助。所以谢谢。
  • @TheElementalofCreation 如果你真的想要,从"rb" 中删除b 会将文件读取为文本而不是字节,这会将所有\r\ns 转换为\n。跨度>
  • 非常正确,但是这是更大代码的一部分,并且 readAll() 函数在其中被大量用于读取必须使用“rb”的文件
猜你喜欢
  • 1970-01-01
  • 2017-03-01
  • 2014-08-04
  • 2016-02-13
  • 1970-01-01
  • 2012-02-23
  • 2021-11-02
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多