首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Lua -创建Detours的函数

Lua -创建Detours的函数
EN

Stack Overflow用户
提问于 2015-06-05 01:01:48
回答 1查看 529关注 0票数 0

我需要对不同的功能做几个弯路,一个接一个地做,这不是一个选择。我正在寻找一个函数,理想情况下,这个函数将接受一个表,这个表是类。循环遍历它,对于每个键,作为函数的值对在原始函数名之前创建一个带有前缀的函数指针。我试过几种不同的方法来达到这一效果,但它们都产生了不同的问题。一些简单地不会绕道指针,不管你给他们什么,另一些做绕道指针,但它们不工作,有些会溢出堆栈或根本不被识别。

我想知道是否有一种方法,即rawsets、metatable重写、常量循环直到它们匹配,等等,这样函数就可以得到一个表(或者一个与表同名的字符串,因此加载字符串方法也在这里工作),并循环每个函数,并使一个工作弯路的pointer...no重要。

我更喜欢使用self:prefix_orig_name(.)语法..。可以用实际的args代替。

这里有两个变体,我试过的例子使用。

代码语言:javascript
复制
-- 1st Method
detours = detours or {}

function detour(object, class) -- Class is an extra arg that I would send if for some reason just sending an object didn't work...it was theory oh'ed
    if detours[object] then -- Check if the detour already exists...might be worth remaking it especially if the function gets overridden several times in different places?
        print("detour: Previous " .. object .. " detour found, using previous detour")
        return
    end
    for name, func in pairs(class and class or loadstring("return " .. object)()) do
        -- the loadstring method here is used because the argument received is a string of the same name as the table...thus loading it will yield a table
        if type(func) == "function" then
            local execute, error = loadstring(object .. ".custom_detour_" .. name .. " = " .. object .. "." .. name) -- This makes the actual pointer
            if error then
                print("detour Error: " .. " Failed to detour: " .. object .. " Error: " .. error)
            end
            local luanch, assert = pcall(execute)
            if not luanch then
                print("detour Error: " .. " Failed to detour: " .. object .. " Error: " .. assert)
            end
        end
    end
    print("Table: " .. object .. " successfully detourd")
    detours[object] = true -- tells us we made a detour of this table/string
end

-- 2nd Method
function detour(object) -- Takes a table
    for k, v in pairs(object) do
        if type(v) == "function" and not detours[k] then
            if not object.custom_detour_ then
                object.custom_detour_ = clone(object) -- use a simple cloning function (shallow) to put a clone of the main table into a sub table of the main table
            end
            if object["custom_detour_" .. k] ~= object.custom_detour_[k] then
                object["custom_detour_" .. k] = object.custom_detour_[k] -- this makes it so the self:custom_detour_orig_name(...) syntax can be used, if I am not mistaken
            end
        end
    end
end

-- Example Usage:
MyClass = class() -- class function is relatively OOP standard

function MyClass:init()
    self._something = true
end

function MyClass:change(value)
    self._something = value
end

function MyClass:table_print(tbl) -- just making funcs up
    for k, v in pairs(tbl) do
        print(v)
    end
end

my_class = MyClass:new()

-- 1st Method
detour("MyClass")

--2nd Method
detour(MyClass)

我个人更喜欢第一种方法,或者至少是一个字符串,因为我可以记录每一条弯路,如果稍后出现问题,它会使我的调试easier...but工作起来。

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2015-06-05 01:17:12

简单的绕行很容易用闭包;不需要loadstring

代码语言:javascript
复制
function detour(cls)
    local detours = {}
    for key, value in pairs(cls) do
        if type(value) == "function" then -- note: ignores objects with __call metamethod
            detours["custom_detour_"..key] = function(...)
                -- Do whatever you want here
                return value(...)
            end
        end
    end
    for key, value in pairs(detours) do
        cls[key] = value
    end
end
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/30656700

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档