【问题标题】:Using Lua, check if file is a directory使用 Lua,检查文件是否是目录
【发布时间】:2019-08-09 07:30:24
【问题描述】:

如果我有这个代码

local f = io.open("../web/", "r")
print(io.type(f))

-- output: file

我如何知道f 是否指向目录?

【问题讨论】:

  • 我很确定 f 在那里会为零,因为尝试使用 io.open 打开目录应该返回 nil 和类似 error opening "../web/": is a directory 的字符串(在 Windows 上我得到../web/: Permission denied)

标签: lua


【解决方案1】:

ANSI C 没有指定任何获取目录信息的方法,所以 vanilla Lua 不能告诉你这些信息(因为 Lua 力求 100% 的可移植性)。但是,您可以使用 LuaFileSystem 等外部库来识别目录。

Progamming in Lua 甚至明确声明了缺少的目录功能:

作为一个更复杂的例子,让我们编写一个返回给定目录内容的函数。 Lua 在它的标准库中没有提供这个函数,因为 ANSI C 没有这个函数。

该示例继续向您展示如何自己在 C 中编写 dir 函数。

【讨论】:

    【解决方案2】:

    我在我使用的库中找到了这段代码:

    function is_dir(path)
        local f = io.open(path, "r")
        local ok, err, code = f:read(1)
        f:close()
        return code == 21
    end
    

    我不知道 Windows 中的代码是什么,但在 Linux/BSD/OSX 上它可以正常工作。

    【讨论】:

    • 这也会为空文件返回true
    【解决方案3】:

    如果你这样做

    local x,err=f:read(1)
    

    那么您将在err 中获得"Is a directory"

    【讨论】:

    • 请注意,错误信息(如果它来自系统)可能是本地化的,因此依赖它可能不是一个好主意。
    • 当然,您可以通过在运行时故意引起错误来收集一些本地化系统错误消息的参考样本,并使用该目录来决定......现在问题是错误列表本身也不是真正可移植的。例如,在某些符合标准的 C 环境中甚至可能没有目录的概念。
    【解决方案4】:

    Lua 的默认库无法确定这一点。

    但是,您可以使用第三方 LuaFileSystem 库来访问更高级的文件系统交互;它也是跨平台的。

    LuaFileSystem 提供 lfs.attributes 可以用来查询文件模式:

    require "lfs"
    function is_dir(path)
        -- lfs.attributes will error on a filename ending in '/'
        return path:sub(-1) == "/" or lfs.attributes(path, "mode") == "directory"
    end
    

    【讨论】:

    • 这个。使用 LFS。在苏联 Lua 中,可移植性会伤害您。
    【解决方案5】:

    至少对于 UNIX:

    if os.execute("cd '" .. f .. "'")
    then print("Is a dir")
    else print("Not a dir")
    end
    

    :)

    【讨论】:

      【解决方案6】:
      function fs.isDir ( file )
      if file == nil then return true end
      if fs.exists(file) then
          os.execute("dir \""..userPath..file.."\" >> "..userPath.."\\Temp\\$temp")
          file = io.open(userPath.."\\Temp\\$temp","r")
          result = false
          for line in file:lines() do
              if string.find(line, "<DIR>") ~= nil then
                  result = true
                  break
              end
          end
          file:close()
          fs.delete("\\Temp\\$temp")
          if not (result == true or result == false) then
              return "Error"
          else
              return result
          end
      else
          return false
      end
      end
      

      这是我从之前找到的库中提取的一些代码。

      【讨论】:

      • 不幸的是,我没有。但是我发现如果您将 userPath 变量更改为您的项目所在的目录,创建 Temp 文件夹并使用它,应该不会有任何错误。
      • hmmm - 你怎么能从图书馆拉东西却不知道从哪里拿来的?你应该总是在值得称赞的地方给予信任。
      【解决方案7】:

      这首先检查路径是否可以读取(对于空文件也是nil),然后另外检查大小不为0。

      function is_dir(path)
          f = io.open(path)
          return not f:read(0) and f:seek("end") ~= 0
      end
      

      【讨论】:

        猜你喜欢
        • 2015-11-11
        • 2011-06-26
        • 2010-11-23
        • 1970-01-01
        • 2018-05-08
        • 1970-01-01
        • 2022-01-04
        相关资源
        最近更新 更多