功能组件中的 React Native const vs let vs var

React Native const vs let vs var in Functional Components

这是一个更广泛的问题,涉及在 React 原生功能组件(与 class 组件相对)中使用不同的变量声明,特别是 let 与 const 的使用,以及它们如何受渲染和影响这样的。对于这个问题,当我说'render'或're-render'时,我说的是render function的执行(像下面的'MyFunctionalComponent'),不一定一个 UI update/change.

根据我的理解,与普通 js 不同,const 变量在 react/react 原生中并不完全是 'constant',并且可以像这样更改(使用钩子?):

export default function MyFunctionalComponent() {

    const [test, setTest] = useState(false);

    const testFunction = () => { //some sort of function, maybe called by a button press
        setTest(true); //this can change test, but something like 'test = true' throws an error
    }
}

但是根据我的理解,let 可以采取类似的行为:

export default function MyFunctionalComponent() {


    let test = false

    const testFunction = () => { //some sort of function, maybe called by a button press
        test = true;
    }
}

但是,我看过的大多数 React 本机示例和教程等似乎总是使用 const 语法,即使它似乎涉及更多代码。为什么?个人喜好,还是必需品? const 做事的方式是否以某种方式 re-render/re-call MyFunctionalComponent 具有 const 变量的新值?

接下来,我不确定导致这种情况的确切行为,但有时在功能组件内部使用 const 语法时,变量会在渲染调用之间更改并保存状态,有时,const 变量会被重置每次渲染被调用时都恢复到默认状态。 (我知道这部分含糊不清,所以如果不够详细请忽略它)为什么会这样?

同样,当在功能组件外部而不是内部创建 const 时,我看到了不同的行为...作用域是否像您期望的那样工作?它们(还是?)在新的渲染调用中重新实例化了吗? 'setState' 是否调用重新渲染?缩短前面的问题,为什么我的一些常量在重新渲染时保留它们的状态,而有些似乎重置为默认值?

var属于什么地方,是和普通js一样,还是也受react的影响? (我觉得我已经掌握了常规 js 中这些变量声明的差异,但是这种 const 行为与 react 让我质疑这一切)。

所以总的来说,问题基本上是,let、var 和 const 的 differences/advantages 是什么,特别是在 react/react 原生中,它们与常规 javascript 有何不同?

最后,class组件和React Native中的功能组件有区别吗?

感谢您阅读这么长的问题。

Personal preference, or necessity?

仅偏好和风格。

使用const而不是varlet来声明有状态变量使得代码的意图更加清晰。这不是必需的 - 如果使用 varlet,你看到的几乎所有组件都可以正常工作 - 但它会给阅读代码的人带来轻微的混淆。

React 是用 JavaScript 编写的。 React 中的状态变量,用 const 声明,不能重新分配,就像在普通的 JavaScript 中一样。您缺少的关键是组件函数每次重新渲染时都会再次调用 ,导致 useState 函数的调用返回不同的值。

有关如何使用 const 并多次调用一个函数在 vanilla JS 中工作的快速示例:

let i = 0;
const getI = () => i;
const fn = () => {
  const theValue = getI();
  console.log(theValue);
  i++;
  setTimeout(fn, 1000);
};
fn();

并不是变量被重新赋值(因为使用const会被禁止),而是整个函数再次运行,导致一个新的值被赋值给用[声明的变量=13=] 在其新的初始化时刻。

Next, I'm not sure the exact behavior that is causing this, but sometimes when using the const syntax inside the functional component, the variables change and save state between render calls, and sometimes, a const variable is reset to its default state every time the render is called. (I know this part is vague, so feel free to ignore it if there is not enough detail) Why does this happen?

您可能指的是陈旧的关闭问题。如果导致差异的变量绑定来自 先前 渲染,而不是当前渲染,就会发生这种情况。

为了快速了解在 vanilla JS 中可能是什么样子,根据上面的代码片段改编,我将在第一个渲染器上添加一个超时,这将只导致第一个渲染器的 i正在使用的渲染:

let i = 0;
const getI = () => i;
const fn = () => {
  const theValue = getI();
  console.log(theValue);
  if (theValue === 0) {
    // first render
    setTimeout(() => {
      console.log('Timeout from first render running, sees a theValue of:', theValue);
    }, 5000);
  }
  i++;
  setTimeout(fn, 1000);
};
fn();

Similarly, I have seen different behavior when consts are created outside of the functional component instead of within... does scope work as you would expect with these? Are they (still?) re-instantiated on new render calls?

取决于变量所在的块。如果它在另一个组件中,它可能会被重新初始化。如果它不在另一个组件中,那么它可能不在。例如,通常有一个模块导出一个组件,该组件具有一些绝对不变的 const 值,所有组件都使用这些值声明在顶部,例如

const apiKey = 'someApiKey';
export const ApiInterface = () => {
  // ...
};

关于 constletvar 具体而言,letvar 的问题是它们允许重新分配 - 但唯一在 React 中更改状态变量的正确方法是调用状态 setter,而不是重新分配变量。调用状态 setter 将导致重新渲染;重新分配变量不会导致重新渲染,重新分配变量将导致分配的值在下一次重新渲染时丢失。因此,完全清楚不应重新分配有状态变量是个好主意。

Lastly, does it differ between class components and functional components in react native?

是的,在 class 组件中,状态被保存为实例的 属性(this)。状态不再是一个独立的 const 标识符,而是一个更大对象的 属性,因此在class 组件 - 除非你从状态中提取值并自己将它们放入普通的独立变量中,在这种情况下它们的行为就像任何其他独立变量一样。