设计思路
- 类型守卫函数:针对不同的数据类型(对象、数组等)编写类型守卫函数,用于判断某个值是否具有特定的结构。
- 递归检查:由于对象可能嵌套,需要递归地应用类型守卫函数来处理深层结构。
- 缓存结果:为了避免不必要的类型检查,可以缓存类型检查的结果,尤其是对于频繁访问的属性。
关键代码示例
// 类型守卫函数,判断是否为对象
function isObject(value: any): value is Record<string, any> {
return typeof value === 'object' && value!== null;
}
// 类型守卫函数,判断是否为数组
function isArray<T>(value: any): value is T[] {
return Array.isArray(value);
}
// 安全获取对象深层属性的函数
function safeGet<T, K1 extends keyof T, K2 extends keyof T[K1], K3 extends keyof T[K1][K2]>(
obj: T,
key1: K1,
key2: K2,
key3: K3
): T[K1][K2][K3] | undefined {
if (isObject(obj) && key1 in obj) {
const subObj = obj[key1];
if (isObject(subObj) && key2 in subObj) {
const subSubObj = subObj[key2];
if (isObject(subSubObj) && key3 in subSubObj) {
return subSubObj[key3];
}
}
}
return undefined;
}
// 示例对象
const complexObj = {
a: {
b: {
c: 123
}
}
};
// 使用安全获取函数
const result = safeGet(complexObj, 'a', 'b', 'c');
if (result!== undefined) {
console.log(result); // 输出: 123
}
性能优化
- 缓存机制:可以使用
WeakMap
来缓存类型检查的结果,因为WeakMap
的键是弱引用,不会阻止对象被垃圾回收。
const typeCheckCache = new WeakMap<any, boolean>();
function isObjectCached(value: any): value is Record<string, any> {
if (typeCheckCache.has(value)) {
return typeCheckCache.get(value)!;
}
const result = typeof value === 'object' && value!== null;
typeCheckCache.set(value, result);
return result;
}
- 减少不必要的递归:在递归检查时,可以根据具体业务需求,提前返回结果,避免对深层结构进行不必要的检查。例如,如果已知某个属性不存在,就不需要继续深入检查。