我有一个函数在工作目录的父目录中查找名为“global”的文件。这就是我的想象:
function readglobal()
if isfile("./global")
text = readdlm("./global",String,comment_char='/')
else
for i = 1:8
if isfile("../"^i * "global")
text = readdlm("../"^i * "global",String,comment_char='/')
break
end
end
end
isdefined(:text) || error("Could not find global file")
dict = Dict{String,String}()
for i in 1:size(text)[1]
dict[text[i,1]] = text[i,2]
end
return dict
end
这不起作用,因为 isdefined 在current_module()中查找全局变量,我从中调用函数。 有没有办法让它按预期工作?要在函数中评估 isdefined(:text)吗?
我使用以下代码解决了这个问题,但我认为上面的代码更清晰。
function readglobal()
foundit = isfile("./global")
if foundit
text = readdlm("./global",String,comment_char='/')
foundit=true
else
for i = 1:8
foundit = isfile("../"^i * "global")
if foundit
text = readdlm("../"^i * "global",String,comment_char='/')
break
end
end
end
foundit || error("Could not find global file")
dict = Dict{String,String}()
for i in 1:size(text)[1]
dict[text[i,1]] = text[i,2]
end
return dict
end
答案 0 :(得分:2)
以下是此功能的1.5行版本:
readglobal() = Dict(mapslices(x->=>(x...),readdlm(first(filter(isfile,
"./$("../"^i)global" for i=0:8)),String;comment_char='/'),2))
如果文件丢失,它甚至会返回错误;)
答案 1 :(得分:2)
编辑:不知怎的,我错过了你找到的解决方法,正如你所说的那样,这与我建议的几乎相同。我不同意第一个代码更清晰,使用isdefined
对我来说似乎很苛刻。 foundit
标志是正确的方式,恕我直言。
原始回答:
请勿使用isdefined
检查是否找到了该文件。而是设置一个标志,例如filefound
。这些内容(警告,未经测试):
function readglobal()
filefound = false
filepath = "global"
for i in 0:8
filefound = isfile(filepath)
if filefound
break
end
filepath = joinpath("..", filepath)
end
filefound || error("Could not find file ")
text = readdlm(filepath, String, comment_char='/')
dict = Dict{String,String}()
for i in 1:size(text, 1)
dict[text[i,1]] = text[i,2]
end
return dict
end
编辑2 :这是一个变体:
function readglobal(filename, maxtries=8)
tries = 0
while !isfile(filename) && (tries+=1) <= maxtries
filename = joinpath("..", filename)
end
tries > maxtries || error("Could not find file ")
text = readdlm(filename, ...
...
end
答案 2 :(得分:1)
不是一个确切的答案,但我会使用一个单独的函数:
function get_global_content()
if isfile("./global")
return readdlm("./global",String,comment_char='/')
else
for i = 1:8
if isfile("../"^i * "global")
return readdlm("../"^i * "global",String,comment_char='/')
end
end
end
error("Could not find global file")
end
function readglobal()
text = get_global_content()
dict = Dict{String,String}()
for i in 1:size(text)[1]
dict[text[i,1]] = text[i,2]
end
return dict
end
或者,看看Nullable
,例如,
function readglobalnull()
text = Nullable()
if isfile("./global")
text = Nullable(readdlm("./global",String,comment_char='/'))
else
for i = 1:8
if isfile("../"^i * "global")
text = Nullable(readdlm("../"^i * "global",String,comment_char='/'))
break
end
end
end
isnull(text) && error("Could not find global file")
text = get(text)
dict = Dict{String,String}()
for i in 1:size(text)[1]
dict[text[i,1]] = text[i,2]
end
return dict
end
答案 3 :(得分:0)
Julia的0.7版本有一个@isdefined variable_name
宏,能够正确地完成我在这个问题中所要求的内容。它适用于任何局部变量。