목표는 키의 값에 따라 테이블의 키를 일치시키는 것입니다.루아의 테이블 키 영향 값 (오른쪽)의 키 액세스
example = { ["dummy"] = this .. " example" }
print example.dummy -- print "dummy example"
여기에서 this
은 키를 나타내는 키워드입니다. 루아에서 그렇게 할 수있는 방법이 있습니까?
목표는 키의 값에 따라 테이블의 키를 일치시키는 것입니다.루아의 테이블 키 영향 값 (오른쪽)의 키 액세스
example = { ["dummy"] = this .. " example" }
print example.dummy -- print "dummy example"
여기에서 this
은 키를 나타내는 키워드입니다. 루아에서 그렇게 할 수있는 방법이 있습니까?
직접 수행 할 방법이 없습니다.
당신은 몇 가지 전처리를 할 수있는 :
t = { foo = this .. ' bar' }
this
때문에 항상 키 또는 테이블에 관계없이 표현 될 것이다 :
example = { ["dummy"] = "{THIS} example" }
for k,v in pairs(example) do
example[k]=v:gsub("{THIS}",k)
end
print(example.dummy)
그것은뿐만 깨끗한 식을 가질 수 없습니다. 즉, 표 항목의 값으로 표현식을 캡처 할 수 없습니다.
metatables과 기능을 사용하여 일정 수준의 간접 참조를 구현하는 것은 가능하지만 거의 불가능합니다. 여기서 우리는 fetch-time evaluation을한다. 결과를 다시 계산할 수도 있습니다.
local function indirect_table()
local uptable = {}
return setmetatable({}, {
__index = function (self, key)
local value = uptable[key]
return type(value) == 'function' and uptable[key](key) or value
end,
__newindex = function (self, key, value)
uptable[key] = value
--[[precompute, with no need for an uptable, or __index:
`rawset(self, key, value(key)`]]
end
})
end
local tab = indirect_table()
tab.foo = function (key) return key .. 'bar' end
print(tab.foo) --> 'foobar'
참고 :이 예제는 클로저를 사용하지만, 당신은뿐만 아니라 getmetatable
를 사용하여 패턴의이 종류를 구현할 수 있습니다.
개인적으로, 나는 임의의 키와 값을 허용하고, 자신의 조치가가 지정하는 간접 패턴으로이 추상 것입니다. 이런 종류의 패턴은 주요 값의 결과가 수신 된 입력에 따라 달라지는 손보다는 오히려 프로그래밍 방식으로 주로 사용됩니다. 다시 말하지만 귀엽지는 않지만 좀 더 강건합니다 (선택 사항 동작).
local function I (_, value) return value end
local K = setmetatable({
__call = function (actor, key)
return actor.action(key, actor.value)
end
}, {
__call = function (K, value, action)
return setmetatable({ value = value, action = action or I }, K)
end
})
local T = setmetatable({
__newindex = function (self, key, value)
if getmetatable(value) == K then
value = value(key)
end
rawset(self, key, value)
end
}, {
__call = function (T, o)
return setmetatable(o or {}, T)
end
})
간단한 사용 :
local function concat (left, right) return left .. right end
local t = T {}
t.foo = K('bar', concat) -- with a common action
t.zar = K({}, unknown_action) -- without action (`nil`)
t.qux = 'qaz' -- standard
print(t.foo, t.zar, t.qux)
이 이상한 메타 프로그래밍입니다. 나는 그러한 접근이 필요하다는 추론을 다시 한번 확인한다. 아마도 당신은 XY Problem 함정에 빠졌을 것입니까? 처음에는 존재할 필요가없는 문제에 대한 해결책처럼 느껴집니다.
이 세부적인 솔루션으로 회신 해 주셔서 감사합니다.내 문제가 무엇인지, 그리고 lhf가 제안한 테이블 전처리를 어떻게 처리했는지에 대한 답을 해설했다. – psychoslave
글쎄, 내 주어진 예제에서 작동 할 것이므로 관련 답변이 될 것입니다. 그러나 내가 염두에 두었던 것은 'this'를 키에 영향을받는 익명 함수의 매개 변수로 사용하는 것입니다. 예 : {= "dummy"] = function (k = this) return k .. "example"end' . – psychoslave
@psychoslave, 전처리에서'v'가 함수라면,'example [k] = v (k)'를 실행하십시오. – lhf
@psychoslave 왜 전화를 걸 때 키를 직접 전달하지 않습니까? – warspyking