Интенсивное чтение "Изучение исходного кода"

JavaScript

1. Введение

javascript-knowledge-reading-source-codeВ этой статье рассказывается о важности чтения исходного кода.В серии интенсивного чтения также есть восемь статей из серии исходного кода, а именно:

По собственному мнению автора, программисты, потратившие много исходного кода, обладают следующими характеристиками:

  1. Мышление системное, что в основном выражается в том, что при изменении модуля кода все файлы проекта будут рассматриваться как единое целое, а влияние будет оцениваться заранее.
  2. Мышление дальновидно, а реализованные решения можно быстро оценить на этапе (временные или стандартные или масштабируемые), граничные условия можно решить заранее, а баги фреймворка свести к минимуму.
  3. Реализация кода более элегантная, поддерживается большим опытом работы с исходным кодом.При решении одной и той же проблемы эти программисты могут использовать меньшее количество строк и более подходящую стороннюю библиотеку для решения проблемы, читабельность кода лучше, разделение модулей более разумно и способствует обслуживанию.

Поскольку чтение исходного кода так важно, как мы можем хорошо читать исходный код? Статья, которую я прочитал на этой неделе, — это статья о методах, в которой рассказывается, как лучше читать исходный код.

2. Обзор

Преимущества чтения исходного кода, навыки чтения исходного кода, а также тематические исследования Redux Connect: три части исходных пунктов.

Преимущества чтения исходного кода

Чтение исходного кода полезно для понимания абстрактных понятий, таких как виртуальный DOM; это полезно для исследования проекта, а не только для количества звезд Github; для понимания дизайна превосходной структуры каталогов; знакомство с некоторыми незнакомыми инструментальными функциями также может вас вдохновить Глядя на спецификацию JS, этот подход, основанный на проблемах, также является рекомендуемым автором способом изучения спецификации JS.

Советы по чтению исходного кода

Лучший способ прочитать исходный код — прочитать статью.Если автор исходного кода написал исходный код для интерпретации статьи, это самый трудоемкий способ. Хотя вы можете узнать все детали, глядя непосредственно на код, когда вы не знаете идею дизайна, вы можете не найти направление, просто взглянув на исходный код.Конечная цель чтения исходного кода — найти основная концепция дизайна Если у фреймворка нет собственной основной концепции дизайна, этот фреймворк не стоит того, чтобы его рождали, не говоря уже о том, чтобы его читали. Если автор фреймворка записал основную концепцию фреймворка в статью, то чтение статьи — лучшее решение.

Другой способ - поставить точку останова, написать минимальную программу, установить точку останова на входе и выходе из выполнения фреймворка, а затем следовать пути выполнения, чтобы понять шаг за шагом. Хотя в пути выполнения будет много посторонних функций, мешающих энергии, но если вы достаточно терпеливы, вы обязательно что-то выиграете, когда контрольная точка закончится.

В исходном тексте также упоминался способ просмотра исходного кода, то есть бесцельная охота за сокровищами. В процессе поиска основных идей фреймворка, если вы столкнетесь с некоторыми интересными функциями, вы можете остановиться и внимательно прочитать, и вы можете найти некоторые фрагменты кода, которые вас вдохновят.

Тематическое исследование Redux Connect

В исходном тексте Redux Connect используется как пример для представления исследовательских идей.

После первого знакомства с функцией Connect «компоненты-оболочки» задайте себе два вопроса:

  1. Как Connect реализует упакованный компонент и возвращает его как есть, но улучшает функциональность компонента? (знание компонентов более высокого порядка)
  2. После понимания этого шаблона проектирования, как реализовать его, используя существующую документацию?

Создав базовую программу, использующую Connect:

class MarketContainer extends Component {

}

const mapDispatchToProps = dispatch => {
 return {
   updateSummary: (summary, start, today) => dispatch(updateSummary(summary, start, today))
 }
}

export default connect(null, mapDispatchToProps)(MarketContainer);

Например, из сгенерированной функции подключенияcreateConnectмы можем учитьFacade Pattern- Фасадный режим.

отcreateConnectМесто вызова функции:

export function createConnect({
 connectHOC = connectAdvanced,
 mapStateToPropsFactories = defaultMapStateToPropsFactories,
 mapDispatchToPropsFactories = defaultMapDispatchToPropsFactories,
 mergePropsFactories = defaultMergePropsFactories,
 selectorFactory = defaultSelectorFactory
} = {})

Мы можем изучить точки знаний о деструктурировании параметров функции по умолчанию.

Короче говоря, в процессе изучения исходного кода вы можете узнать некоторые новые функции JS, некоторые шаблоны проектирования, это дополнительные сокровища, и постоянно понимать и учиться применять это к написанному вами фреймворку, чтобы достичь цели. изучения исходного кода.

3. Интенсивное чтение

Исходный текст знакомит с двумя методами изучения исходного кода и использует Redux Connect в качестве примера, чтобы проиллюстрировать, что многие периферийные знания могут быть изучены в процессе изучения исходного кода, что нам очень помогло.

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

Суть исходного кода Immerjs

Immer позволяет нам обновлять объекты изменяемым образом, в результате чего получается неизменяемый объект:

this.setState(produce(state => (state.isShow = true)))

Подробную интерпретацию исходного кода можно прочитатьздесь.

Основная идея состоит в том, чтобы использовать прокси для выполнения грязной работы. В приведенном выше примереstateуже является прокси (Proxy) объектом, по настраиваемомуsettingПродолжайте рекурсивно делать неглубокие копии и, наконец, возвращайте новый объект верхнего уровня, на который ссылаются, какproduceВозвращаемое значение.

От Immerjs мы узнали, что прокси может превратить искажение в магическое использование, что более интуитивно понятно, чем чтение любой вводной статьи о прокси.

Суть исходного кода sqrn

skorn — это форма sql, например:

const sq = require("sqorn-pg")();

const Person = sq`person`,
  Book = sq`book`;

// SELECT
const children = await Person`age < ${13}`;
// "select * from person where age < 13"

Подробную интерпретацию исходного кода можно прочитатьздесь

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

Из scorn мы узнали, как реализовать цепочкуinit().a().b().c().print()В конечном итоге получается всеобъемлющий результат.Принцип заключается в том, что постоянно изменяемый объект поддерживается внутри. Независимо от внешнего интерфейса React Vue или внутреннего фреймворка Koa и т. д. обычно есть встроенный контекст, и фреймворк, реализующий этот элегантный синтаксис, обычно поддерживает контекст внутри.

Суть исходного кода Epitath

Epitath появился раньше React Hooks и решил проблему ада функций высшего порядка:

const App = epitath(function*() {
  const { count } = yield <Counter />
  const { on } = yield <Toggle />

  return (
    <MyComponent counter={count} toggle={on} />
  )
})

<App />

Подробную интерпретацию исходного кода можно прочитатьздесь

Его суть заключается в использованииgeneratorИтерация компонента React восстанавливает горизонтальную структуру компонента React до вложенной структуры и сглаживает вложенный метод записи:

yield <A>
yield <B>
yield <C>
// 等价于
<A>
  <B>
    <C />
  </B>
</A>

Из эпитафии мы узнаем, чтоgeneratorОказывается, его можно использовать таким образом, потому что его выполнение представляет собой несколько итераций, поэтому мы можем использовать эту функцию для изменения структуры выполнения кода.

Htm — Суть исходного кода Hyperscript

Htm естественным образом интегрирует синтаксис шаблона в html:

html`
  <div class="app">
    <${Header} name="ToDo's (${page})" />
    <ul>
      ${todos.map(
        todo => html`
          <li>${todo}</li>
        `
      )}
    </ul>
    <button onClick=${() => this.addTodo()}>Add Todo</button>
    <${Footer}>footer content here<//>
  </div>
`;

Подробную интерпретацию исходного кода можно прочитатьздесь

Суть в том, как получить AST элемента dom по шаблону? После получения AST удобно генерировать последующий контент.

Авторский подход таков:

const TEMPLATE = document.createElement("template");
TEMPLATE.innerHTML = str;

Таким образом, TEMPLATE поставляется со своим собственным синтаксическим анализом AST, который использует собственный синтаксический анализ AST браузера для получения AST. Из Htm мы узналиinnerHTMLСтандартный AST может быть сгенерирован, поэтому, пока есть операционная среда браузера, когда вам нужно получить AST, никакая другая библиотека не нужна.innerHTMLявляется лучшим решением.

Суть исходного кода React PowerPlug

React PowerPlug — это библиотека инструментов для управления состоянием с использованием свойств рендеринга.

Он может подключать управление состоянием с произвольной степенью детализации в JSX:

<Value initial="React">
  {({ value, set, reset }) => (
    <>
      <Select
        label="Choose one"
        options={["React", "Preact", "Vue"]}
        value={value}
        onChange={set}
      />
      <Button onClick={reset}>Reset to initial</Button>
    </>
  )}
</Value>

Подробную интерпретацию исходного кода можно прочитатьздесь

Ядром этой библиотеки является использование реквизитов рендеринга для решения проблем управления локальным состоянием JSX Чтение исходного кода, чтобы понять использование реквизитов рендеринга, является самой большой ценностью, которую этот исходный код приносит вам.

Суть синтаксического анализатора исходного кода

синтаксический парсер — это JS-версия генератора синтаксического парсера. Автор также является автором. Как им пользоваться:

import { createParser, chain, matchTokenType, many } from "syntax-parser";

const root = () => chain(addExpr)(ast => ast[0]);

const addExpr = () =>
  chain(matchTokenType("word"), many(addPlus))(ast => ({
    left: ast[0].value,
    operator: ast[1] && ast[1][0].operator,
    right: ast[1] && ast[1][0].term
  }));

const addPlus = () =>
  chain("+"), root)(ast => ({
    operator: ast[0].value,
    term: ast[1]
  }));

const myParser = createParser(
  root, // Root grammar.
  myLexer // Created in lexer example.
);

Подробную интерпретацию исходного кода можно прочитатьздесь

Ядром синтаксического анализатора является использование двусвязного списка для реализации парсера с возвратом. Зная эту библиотеку, вы можете самостоятельно реализовать стек вызовов JS и вернуться к предыдущему состоянию выполнения в любое время для повторного выполнения. В то же время исходный код этой библиотеки также улучшит ваше понимание связанных списков и расширит ваше представление о сценариях использования связанных списков.

Суть исходного кода react-easy-state

react-easy-state использует Proxy для создания простого метода управления глобальным потоком данных:

import React from "react";
import { store, view } from "react-easy-state";

const counter = store({ num: 0 });
const increment = () => counter.num++;

export default view(() => <button onClick={increment}>{counter.num}</button>);

Подробную интерпретацию исходного кода можно прочитатьздесь

react-easy-state используетobserver-utilДля достижения основной функции самое ценное, что мы можем извлечь из него, — это дизайнерская концепция объединения Proxy и React, то есть использованиеgetter setterРеализовать двухстороннюю привязку данных и представления, или отслеживание зависимостей, более подробно здесь раскрываться не буду, если интересно, то можете прочитать, что автор писал ранееИзбавьтесь от кокона и реализуйте отслеживание зависимостейодин период.

Суть исходного кода Inject Instance

inject-instance — это класс, реализующий внедрение зависимостей:

import {inject} from 'inject-instance'
import B from './B'

class A {
  @inject('B') private b: B
  public name = 'aaa'

  say() {
    console.log('A inject B instance', this.b.name)
  }
}

Подробную интерпретацию исходного кода можно прочитатьздесь

Для нас есть два основных источника вдохновения: во-первых, мы можем использовать декоратор для хранения некоторой дополнительной информации об объекте, которую мы можем использовать при необходимости, во-вторых, внедрение зависимостей несложно. решена Проблема зависимостей, то есть все циклические зависимости могут быть решены путем добавления родителя.

4. Резюме

Чтение кода не является целью, но целью является понимание основных идей дизайна, лежащих в основе исходного кода. Например, код, написанный человеком, который пишет скаффолдинг и прочитал много исходного кода скаффолдинга, будет сильно отличаться от кода, написанного неопытным человеком.Разрыв между ними — это опыт некоторых шаблонов проектирования, трехсторонних библиотек и структурных дизайн.зазор.

Это слишком ограничено, чтобы изучать только теоретическое пространство, и только смотреть на код слишком ограничено Научиться видеть теорию из кода — лучший способ учиться.

Адрес обсуждения:Интенсивное чтение «Изучение исходного кода» · Выпуск №179 · dt-fe/weekly

Если вы хотите принять участие в обсуждении, пожалуйста,кликните сюда, с новыми темами каждую неделю, выходящими по выходным или понедельникам. Интерфейс интенсивного чтения — поможет вам отфильтровать надежный контент.

Сфокусируйся наАккаунт WeChat для интенсивного чтения в интерфейсе

Заявление об авторских правах: Бесплатная перепечатка - некоммерческая - не производная - сохранить авторство (Лицензия Creative Commons 3.0)