Мои выводы…

Обычно условие должно оцениваться как истинное или ложное. Это отличается от того, как работают условные выражения в js. Вот что я имею в виду:

data.length > 0 && <div />

Компонент отображается только в том случае, если условие слева оценивается как истинное. Но исходя из чистого js, > 0 является избыточным, поэтому я ожидаю, что следующая строка будет работать:

data.length && <div />

Оказалось, что эта строчка не сработает, (как и ожидалось) почему -

В первом случае, если размер массива равен 0, 0 > 0 будет оцениваться как false, поэтому false && [anything really] оценивается как false, поэтому компонент не будет отображаться.

Однако во втором случае, если размер равен 0, 0 && <div /> оценивается как 0<div />. Другими словами, будет отображаться как 0, так и элемент. Исходя из js, я ожидал, что оператор && приведёт 0 в левой части к логическому (false), но этого не происходит, поэтому они оба отображаются - как работает jsx?

Вы ожидаете, что оператор 0 && <div /> оценивается как false. На самом деле это было бы так, если бы не jsx.

const value = data.length ? 1 : 0;

Вышеупомянутый оператор присваивает value 1, если размер больше 0, и 0 в противном случае, что я считаю очень детерминированным, чем аналог jsx. Я понимаю, что принуждение к отрицательному результату верно, но длина не может быть -ve - я могу ошибаться.

Как насчет приведенного ниже утверждения, как вы думаете, каким будет результат?

data.length ? <div />: <err />;

Вот где это сбивает с толку. Это имеет тенденцию противоречить тому, что мы обсуждали ранее. На самом деле он работает так же, как и в обычном js.

Итак, угадайте, что все сводится к тому, как операторы binary (&&) и ternary (? :) обрабатывают условные выражения в jsx - один приводит к (тернарному), а другой - нет (двоичному).

Как насчет того, чтобы мы переключили операнды бинарного оператора

<div /> && data.length > 0

Это может быть проблемой для большинства новичков. Что происходит, так это то, что компонент будет отображаться независимо от оценки справа! Странно, правда?

Я знаю людей, которые вообще избегают бинарного оператора в jsx из-за его недетерминированной природы. Они используют троичную систему и предоставляют null в качестве операнда, когда они не хотят, чтобы для конкретной оценки ничего не отображалось.

Я также обнаружил, что приведенные выше правила одинаковы для динамических className.

Допустим, у вас есть компонент, который указывает текущий шаг в процессе, и вы хотите придать ему другой цвет / поведение, расширив стили для всех компонентов шага.

<div className={`step ${current ? 'current' : ''}`} />

Когда вы исследуете компонент в инструментах разработки, описанный выше подход создает второй класс (который отображается как дополнительное пространство) в DOM для устаревших компонентов. Если бы был селектор space (может быть, я не знаю), это могло бы привести к конфликту имен.

Как насчет использования операнда null для ложной оценки?

<div className={`step ${current ? 'current' : null}`} />

Ну, вы правильно угадали - это добавляет null к списку разделенных пробелами имен классов для остальных элементов. Снова хаос.

Как насчет двоичного кода? Ну что ж, посмотрим ...

<div className={`step ${current && 'current'}`} />

Оказывается, это, казалось бы, элегантное решение тоже работает, но та же проблема, что и выше - вы получаете false в качестве имени класса для нетекущих элементов.

Мне больше всего нравится пустая строка '' для ложной оценки. Сообщите мне, какой метод вы используете.

Если вы разработали свой компонент так, как вы это сделали, вы не будете наследовать какие-либо стили, как я делаю выше (где все текущие и не текущие компоненты имеют родительский класс step) - и, вероятно, вы захотите продублировать некоторые правила. (какой ущерб) тогда проблема может стать намного проще:

<div className={current ? 'current' : 'not-current'} />

Таким образом, компоненты принимают совершенно разные классы в зависимости от своего состояния. Это может потребовать дублирования пары правил, но, похоже, решит предыдущую проблему. Задача состоит в том, чтобы синхронизировать два класса!

Тем не менее, мой фаворит - ''.