这个 switch 语句是如何工作的?案例值似乎在调试器中未定义

How does this switch statement work? The case values appear to be undefined in the debugger

我想了解这段代码是如何工作的,因为它似乎不应该,但它确实有效。

这是我不理解的某种 TypeScript 魔法吗?反应魔法?如果案例不是字符串,而是显示为 undefined?

的导入值,这将如何工作
Code source
import DialogTitle, { DialogTitleProps } from "./Title";
import DialogDescription, { DialogDescriptionProps } from "./Description";
import DialogButton, { DialogButtonProps } from "./Button";

// ....

  React.Children.forEach(children, (child) => {
    if (typeof child === "object" && child !== null && "type" in child) {
      switch (child.type) {
        case DialogTitle: // DialogTitle is undefined in the debugger when hovered
          titleChildrens.push(child as TitleElement);
          return;
        case DialogDescription: // DialogDescription is undefined in the debugger when hovered
          descriptionChildrens.push(child as DescriptionElement);
          return;
        case DialogButton: // DialogButton is undefined in the debugger when hovered
          if (Platform.OS === "ios" && buttonChildrens.length > 0) {
            buttonChildrens.push(
              <View
                style={[
                  verticalButtons
                    ? styles.buttonSeparatorVertical
                    : styles.buttonSeparatorHorizontal,
                  buttonSeparatorStyle,
                ]}
              />
            );
          }
          buttonChildrens.push(child as ButtonElement);
          return;
      }
    }
    otherChildrens.push(child);
  });

您在调试器中看到的代码不是正在执行的代码。你看到的 Container.tsx 实际上可能只是一个巨大的 bundle.js 某处编译的纯 JS 片段。

Typescript 代码在浏览器可以读取之前需要编译。作为此步骤的一部分,它还会生成源映射,将编译后的代码映射回原始源文件。 Webpack 或您正在使用的任何捆绑器可能会进行自己的编译,并制作新的源映射。

在大多数情况下,这使得调试更容易,但它并不完美。所以你认为 DialogTitle 可能是一个标识符,在编译、缩小、混淆、捆绑等过程中以某种方式进行了转换...

您可以 更清楚地了解正在发生的事情,尽管您调试的代码可能开始看起来很神秘。

源映射通常工作得很好,但我观察到并不是所有的工具都能完美地生成它们。


至于 switch 语句的工作原理,函数有一个标识,可以通过 switch 语句查询。

例如,这是可行的,因为 MyComponent 被分配了 AB,并且每个 case 都可以测试它。

function A() { return <>A</> }
function B() { return <>B</> }

const MyComponent = Math.random() > 0.5 ? A : B

switch(MyComponent) {
  case A: console.log('got A'); break
  case B: console.log('got B'); break
}
// logs "got A" or "got B"

See playground


In the code I referenced, it's switch(child.type) and I don't understand how child.type is compared against a function? child.type is itself a function, but I'm still very confused about how that comparison evaluates to true.

这有点深入到 React 内部,所以我不能保证 为什么 但这似乎是正在发生的事情。

当一个组件呈现时,它 returns 一个 JSX.Element 对象。该对象上似乎有一个 type 属性,它是对呈现该 JSX 的组件的引用。

例如:

function A() { return <>A</> }
console.log(<A />);

在控制台中产生这个:

这意味着渲染的 JSX 会记住通过 type 属性 渲染它的组件。此处的此循环检查是否有任何子项使用可能需要特殊处理的特定组件渲染。

Here's a minimal example 这更接近于您的原始代码段实际执行的操作。