2014-11-26 2 views
3

이것은 왜 내가 불가능했는지 항상 궁금해 한 질문입니다. 완벽한 복제 기능을 만들 수없는 이유는 무엇입니까? 루아 5.3에는 table.copy 함수가 포함되어 있지 않습니다 ... 모든 문제/케이스를 처리한다고 가정합니다.루아 : 완벽한 복제 기능, 왜 안 되니?

몇 가지 이유를 완벽하게 복제 또는 복사를 설명 할 수 https://gist.github.com/MihailJP/3931841https://gist.github.com/tylerneylon/81333721109155b2d244 : 다양한 복제 기능으로

나는 ...이 (얕은 깊이, 재귀, 등)처럼

function deep (t) -- deep-copy a table 
    if type(t) ~= "table" then return t end 
    local meta = getmetatable(t) 
    local target = {} 
    for k, v in pairs(t) do 
     if type(v) == "table" then 
      target[k] = clone(v) 
     else 
      target[k] = v 
     end 
    end 
    setmetatable(target, meta) 
    return target 
end 

function shallow (t) -- shallow-copy a table 
    if type(t) ~= "table" then return t end 
    local meta = getmetatable(t) 
    local target = {} 
    for k, v in pairs(t) do target[k] = v end 
    setmetatable(target, meta) 
    return target 
end 

function copy1(obj) 
    if type(obj) ~= 'table' then return obj end 
    local res = {} 
    for k, v in pairs(obj) do res[copy1(k)] = copy1(v) end 
    return res 
end 


function copy2(obj) 
    if type(obj) ~= 'table' then return obj end 
    local res = setmetatable({}, getmetatable(obj)) 
    for k, v in pairs(obj) do res[copy2(k)] = copy2(v) end 
    return res 
end 

function copy3(obj, seen) 
    if type(obj) ~= 'table' then return obj end 
    if seen and seen[obj] then return seen[obj] end 
    local s = seen or {} 
    local res = setmetatable({}, getmetatable(obj)) 
    s[obj] = res 
    for k, v in pairs(obj) do res[copy3(k, s)] = copy3(v, s) end 
    return res 
end 

소스 것을 의미 기능을 만들 수 없습니까?

+5

* 완벽한 *을 정의하십시오. – lhf

+0

모든 상황, 사건 발생 등을 처리합니다. 즉 사용자가 복제 할 원하는 테이블을 입력하고 그것을 1 : 1로 복사합니다 (다른 이름 또는 다른 이름으로) – B1313

+4

복제 : 'local t; t = {function() return t; 끝}' –

답변

5

@ lhf의 으로 확장하십시오. 나는 루아 메이어 (Lua maillist)에서 여러 차례 토론 된 적이 있다고 생각하는데, 나는 그 이유가 두 가지라고 말하고 싶다. (1) 하나의 경우에 완벽하고 합리적인 것이고, 다른 것에는 과잉이다. (2) metamethods, upvalues ​​및 순환 참조 때문에 다양한 케이스를 다루는 것이 어렵습니다 완벽하게. 예를 들어, metamethod를 사용하여 프록시 테이블을 제공한다고 가정 해보십시오. 이제, 복제 된 테이블 중 두 개가 동일한 프록시 테이블을 공유하며, 하나가 저장된 테이블은 다른 테이블에서 볼 수 있습니다. 이것은 "완벽한"복제품인가요?

더 철학적이지만 관련성이 높은 메모입니다. 객체가 가지고있는 외부 링크로 인해 완벽을 성취하기가 어렵습니다 (그리고 클론 일 수 있습니다.은이를 보존해야합니다). 당신은 집을 소유하고 있습니다. 당신의 완벽한 복제품이 같은 집을 소유하고 있습니까? 당신은 지금 각각 집의 50 %를 소유하고 있습니까? 세 번째 클론은 어때? 아니면 행복하게 결혼했다. 클론은 어때? 배우자도 복제해야합니까? 이 경우 완벽한 곳과 불완전한 곳은 어디입니까?

깊은 사본과 얕은 사본의 차이점을 염려 할 때쯤에는 자신 만의 기능을 쓸 수 있습니다.