You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

TypeScript中declare function编译后被忽略,运行报错求解

问题原因与解决方案

为什么declare function会被"忽略"?

declare function是TypeScript的类型声明语法,它仅负责给TypeScript编译器提供类型校验依据,不会被编译成任何JavaScript运行时代码。你编译后的JS代码里没有makeWatchedObject的实际实现逻辑,运行时自然会报"makeWatchedObject is not defined"的错误,同时person.on也没有对应的运行时处理逻辑。

TS文档里的该示例仅展示类型系统的用法,未提供运行时实现代码,因此你需要自行补充函数的实际逻辑。

完整可运行的实现代码

下面是补充了运行时逻辑的TypeScript代码,编译后可正常执行:

type PropEventSource<Type> = {
    on<Key extends string & keyof Type>(
        eventName: `${Key}Changed`, 
        callback: (newValue: Type[Key]) => void
    ): void;
};

// 移除declare,替换为实际函数实现
function makeWatchedObject<Type>(obj: Type): Type & PropEventSource<Type> {
    // 存储事件回调的映射表
    const eventCallbacks: Record<string, ((value: any) => void)[]> = {};

    // 创建代理对象,拦截属性赋值操作
    const proxy = new Proxy(obj, {
        set(target, prop, newValue) {
            const updateResult = Reflect.set(target, prop, newValue);
            // 属性更新后触发对应变更事件
            const eventName = `${String(prop)}Changed`;
            if (eventCallbacks[eventName]) {
                eventCallbacks[eventName].forEach(callback => callback(newValue));
            }
            return updateResult;
        }
    });

    // 实现on方法,用于注册事件回调
    (proxy as Type & PropEventSource<Type>).on = function<Key extends string & keyof Type>(
        eventName: `${Key}Changed`, 
        callback: (newValue: Type[Key]) => void
    ) {
        if (!eventCallbacks[eventName]) {
            eventCallbacks[eventName] = [];
        }
        eventCallbacks[eventName].push(callback);
    };

    return proxy as Type & PropEventSource<Type>;
}

const person = makeWatchedObject({
    firstName: "Saoirse",
    lastName: "Ronan",
    age: 26
});

person.on("firstNameChanged", newName => {
    console.log(`new name is ${newName.toUpperCase()}`);
});

person.on("ageChanged", newAge => {
    if (newAge < 0) {
        console.warn("warning! negative age");
    }
});

// 测试属性变更,会触发对应回调
person.firstName = "Emily";
person.age = -5;

console.log(person.firstName);

实现说明

  • 使用Proxy拦截对象的属性赋值操作,当属性值变更时自动触发对应的xxxChanged事件
  • 实现on方法,用于注册事件回调并将回调存储在映射表中
  • 属性更新时,根据属性名匹配对应的事件名,执行所有已注册的回调函数

编译后的JavaScript代码会包含完整的运行时逻辑,运行时不再报错。

内容的提问来源于stack exchange,提问作者Grog

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.31 15:40:38