Часто компиляция этих данных в ES5 с помощью Babel's REPL - отличный способ понять, что происходит.
import React from 'react/addons';
let {PropTypes} = React;
становится:
var _addons = require('react/addons');
var _addons2 = _interopRequireDefault(_addons);
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
var PropTypes = _addons2.default.PropTypes;
По сравнению с:
import React, { PropTypes } from 'react/addons';
который становится:
var _addons = require('react/addons');
var _addons2 = _interopRequireDefault(_addons);
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
Первые два оператора в каждой из них идентичны. Операторы импорта становятся вызовами require
, тогда есть вспомогательная функция времени выполнения, которая извлекает соответствующее значение изнутри модуля.
На данный момент это становится интересным. В примере 1 используется деструктуризация объекта, чтобы ввести PropTypes
в качестве новой переменной. Бабель вводит новые переменные в качестве ссылок, указывающих на соответствующие свойства.
var PropTypes = _addons2.default.PropTypes;
Так почему же эта строка кода отсутствует в примере 2? На самом деле, если вы проверите код, вы заметите, что, хотя похоже, что в области видимости должна быть переменная PropTypes
, ее нет. Немного о тайне?
Дальнейшие эксперименты
Опять же, РЕПЛ Бабеля может помочь нам здесь. Посмотрим, что произойдет, если мы напишем код, который использует PropTypes
и скомпилируем его.
import React, { PropTypes } from 'react/addons';
console.log(PropTypes);
Который становится:
var _addons = require('react/addons');
var _addons2 = _interopRequireDefault(_addons);
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
console.log(_addons.PropTypes);
Несколько важных вещей, чтобы заметить.
- Он собирает ссылки на
PropTypes
в _addons.PropTypes
- Она использует
_addons
не _addons2
(в отличие от примера 1)
Это происходит потому, что { PropType } from
синтаксис в примере 2, не уничтожение того.
Названы Импорт
Если следить за этим в ES2015 specification [15.2.2], мы увидим, этот синтаксис описан как NamedImports.
NamedImports :
{ }
{ ImportsList }
{ ImportsList , }
Этот синтаксис предназначен для извлечения именованные экспорта из импортированного модуля.
Например, если пакет реакции/аддонов был опубликован как модуль ES6, для второго синтаксиса это должно было бы выглядеть так.
export const PropTypes = {
// prop types
};
export default React;
Что компилирует:
Object.defineProperty(exports, "__esModule", {
value: true
});
var PropTypes = exports.PropTypes = {};
// prop types
exports.default = React;
PropTypes
добавляется в качестве имени экспорта в exports
объекта.
Заключение
import React from 'react/addons';
let {PropTypes} = React;
Это общий синтаксис деструктурирующий. Он работает, когда значение exports.default
имеет поле PropTypes
.
import React, { PropTypes } from 'react/addons';
Этот синтаксис предназначен для доступа к названному экспорту. Он работает, когда модуль реакции/аддонов экспортирует именованное значение для PropTypes
и значение по умолчанию для React
.
. Есть ли какие-либо предпочтения в отношении использования какого-либо? –
Это зависит от того, что экспортирует модуль? –