VS Code, ATOM 등 오픈 소스 텍스트 편집기 의 코드 구현 에는 어떤 기교가 있 습 니까?

이 편 은 제 가 알 고 있 는 대답 입 니 다. 원문 은 여기 있 습 니 다. justjavac: VS Code, ATOM 등 오픈 소스 텍스트 편집기 의 코드 실현 중 어떤 기교가 있 습 니까?
V8 을 연구 하 는 것 이 비교적 많 고 vscode 와 아 톰 의 성능 에 도 관심 을 가 졌 습 니 다. 매번 vscode, 아 톰 의 change log 를 한 번 씩 보 겠 습 니 다.가장 기억 에 남 는 것 은 vscode 1.14 의 업데이트 로그 입 니 다. doApply Edits Lines inserted using splice · Issue \ # 351 · Microsoft / monaco - editor: 순환 에서 splice 를 사용 하지 마 십시오.
다음 그림 은 내 가 1 년 전에 달 린 테스트 결과: Inserting an array within an array
300 배 차이.
이전에 vscode 는 또 한 번 큰 성능 을 향상 시 켰 고 버 전 1.9 에서 문법 이 높 은 알고리즘 을 개선 했다.
문법 이 밝 은 과정 은 보통 2 단계 (tokenization 과 render) 로 나 뉜 다. 먼저 소스 코드 를 token 으로 나 눈 다음 에 서로 다른 주제 로 분 단 된 token 을 착색 한다.
tokenization 의 과정 은 위 에서 아래로 한 줄 씩 실행 하 는 것 입 니 다.tokenizer 는 줄 의 끝 에 상 태 를 저장 하고 tokenize 다음 줄 에 서 는 이 상 태 를 사용 합 니 다.이렇게 하면 사용자 가 편집 할 때 전체 파일 내용 을 스 캔 하지 않 고 tokenize 줄 의 일부분 만 다시 해 야 합 니 다.
또 다른 경 우 는 현재 줄 의 입력 이 뒤쪽 (심지어 앞) 줄 에 영향 을 줄 수 있 습 니 다. 이 때 종료 상태 로 사 용 됩 니 다.
1.9 이전 버 전에 서 vscode 는 어떻게 tokenization 을 합 니까?
예 를 들 어 위의 코드:
vscode 종류 에 이렇게 저장:
tokens = [
    { startIndex:  0, type: 'keyword.js' },
    { startIndex:  8, type: '' },
    { startIndex:  9, type: 'identifier.js' },
    { startIndex: 11, type: 'delimiter.paren.js' },
    { startIndex: 12, type: 'delimiter.paren.js' },
    { startIndex: 13, type: '' },
    { startIndex: 14, type: 'delimiter.curly.js' },
]

{startIndex: 0, type: 'keyword. js'} 0 부터 시작 하 는 token 은 keyword 임 을 표시 합 니 다.
VSCode 팀 은 블 로그 종 에서 크롬 에서 648 개의 바 이 트 를 차지 하기 때문에 이러한 대상 을 메모리 에 저장 하 는 대가 가 매우 높다 고 지적 했다. (각 대상 의 인 스 턴 스 는 원형 을 가리 키 는 공간 과 그 속성 목록 등 을 유지 해 야 한다.)15 글자 에 648 바 이 트 를 저장 하 는 것 은 받 아들 일 수 없습니다.
따라서 vscode 는 token 을 저장 하기 위해 바 이 너 리 를 사용 합 니 다.
//     0        1               2                  3                      4
map = ['', 'keyword.js', 'identifier.js', 'delimiter.paren.js', 'delimiter.curly.js'];
tokens = [
    { startIndex:  0, type: 1 },
    { startIndex:  8, type: 0 },
    { startIndex:  9, type: 2 },
    { startIndex: 11, type: 3 },
    { startIndex: 12, type: 3 },
    { startIndex: 13, type: 0 },
    { startIndex: 14, type: 4 },
]

위의 표현법 에 비해 type 을 문자열 에서 숫자 로 바 꾸 었 을 뿐 본질 적 으로 많은 메모 리 를 절약 하지 못 했다.하지만 조급해 하지 마 세 요. vscode 에는 블랙 테 크 놀 로 지 도 있어 요.
자 바스 크 립 트 는 IEEE - 754 표준 을 사용 하여 이중 정밀도 부동 소수점 을 저장 하고 꼬리 수 는 53bit 라 는 것 을 잘 알 고 있 습 니 다.정밀 도 를 잃 지 않 고 처리 할 수 있 는 최대 정 수 는 2 ^ 53 - 1 입 니 다.따라서 vscode 는 그 중의 48big 를 사용 하여 인 코딩 을 합 니 다. 32bit 를 사용 하여 startIndex 를 저장 하고 16bit 를 사용 하여 type 을 저장 합 니 다.그래서 위의 대상 은 vscode 종 에 저 장 됩 니 다.
tokens = [
                 //       type                 startIndex
     4294967296, // 0000000000000001 00000000000000000000000000000000
              8, // 0000000000000000 00000000000000000000000000001000
     8589934601, // 0000000000000010 00000000000000000000000000001001
    12884901899, // 0000000000000011 00000000000000000000000000001011
    12884901900, // 0000000000000011 00000000000000000000000000001100
             13, // 0000000000000000 00000000000000000000000000001101
    17179869198, // 0000000000000100 00000000000000000000000000001110
]

각 숫자 는 64bit (8 바이트) 이 고 모두 7 개의 숫자 입 니 다. 이 요 소 를 저장 하려 면 모두 7 * 8 = 56 바이트 가 필요 합 니 다. 게다가 배열 의 추가 비용 은 모두 104 개의 바이트 가 필요 합 니 다. 이전의 648 바이트 의 1 / 6 만 필요 합 니 다.
테마의 렌 더 링 은 Trie 데이터 구 조 를 사 용 했 습 니 다.
이 《 데이터 구 조 》 를 배 운 사람 은 모두 알 고 있 기 때문에 기예 음교 라 고 할 수 없 으 며 전개 되 지 않 는 다.
이 모든 것 은 2017 년 3 월 발 표 된 vscode 1.9 다.
올해 3 월 에는 vscode 가 Text Buffer 를 다시 썼 다.사용 자 는 편집 기 를 사용 합 니 다. 대부분의 시간 은 새 코드 를 쓰 고 오래된 코드 를 바 꾸 는 것 입 니 다. 결국 text 를 편집 하 는 것 입 니 다.
고성능 텍스트 작업 에 대해 vscode 는 처음에 C + + 를 사용 하여 작성 하려 고 시 도 했 습 니 다. 왜냐하면 C + + 의 성능 은 JavaScript 보다 훨씬 높 지만 사실은 이상 적 이지 않 습 니 다. C + + 를 사용 하면 메모리 가 절약 되 었 습 니 다. 그러나 C + 모듈 을 사용 할 때 JavaScript 와 C + + 사 이 를 몇 번 왕복 해 야 합 니 다. 이것 은 vscode 의 성능 을 크게 떨 어 뜨 렸 습 니 다.
vscode 팀 은 Vyacheslav Egorov 의 글 Maybe you don 't need Rust and WASM to speed up your JS 에서 V8 엔진 의 성능 을 어떻게 충분히 압착 하 는 지 에 대한 깨 달 음 을 얻 었 다.mrale. ph 의 블 로 그 를 나 는 거의 모든 편 을 읽 고 매우 고전적 이 며 이해 하기 어렵다.
대부분의 편집 기 는 줄 에 기반 을 두 고 있 습 니 다.프로그래머 가 코드 를 한 줄 씩 작성 하고 컴 파일 러 는 줄 기반 피드백 정 보 를 제공 합 니 다. 스 택 추적 은 줄 번 호 를 포함 하고 tokenization 엔진 은 한 줄 씩 실 행 됩 니 다. vscode 의 초기 버 전에 서도 모든 줄 코드 를 문자열 로 배열 에 직접 저장 합 니 다.
그러나 이런 방식 에는 문제 가 있다.
  • 모든 내용 을 배열 에 읽 으 면 메모리 가 부족 할 수 있 기 때문에 큰 파일 을 열 수 없습니다.
  • 파일 이 크 지 않 아 도 줄 수가 너무 많아 열 수 없습니다.예 를 들 어 사용자 가 35MB 파일 을 열 수 없습니다.근본 적 인 원인 은 이 파일 의 줄 수가 너무 많아 서 1370 만 줄 이다.엔진 은 ModelLine 의 줄 과 대상 마다 약 40 - 60 개의 바이트 를 사용 하기 때문에 전체 배열 은 약 600 MB 의 메모리 로 문 서 를 저장 합 니 다.그 러 니까 이 35M 파일 을 열 려 면 600 M 의 내용 이 20 배 필요 하 다 는 거 야!!!
  • 또 다른 문 제 는 속도 다.이 배열 을 구축 하기 위해 서 는 줄 마다 문자열 대상 을 얻 을 수 있 도록 줄 바 꿈 자 를 통 해 내용 을 분할 해 야 합 니 다.

  • 그래서 vscode 는 새로운 데이터 결 과 를 찾기 시 작 했 고 결국 Piece table 을 선택 했다.왜 이렇게 늦게 piece table 을 선 택 했 는 지 모 르 겠 지만 마이크로소프트 오 피 스 워드 에서 piece table 을 사용 한 지 알 아야 합 니 다.저도 자바 에서 워드 를 읽 은 jar 패키지 소스 코드 에서 처음 알 게 된 piece table 데이터 구조 입 니 다.
    연장 읽 기 를 추천 하 는 글 몇 편:
  • Emacs 편집기 의 buffer 논문: Flexichain: An editable sequence and its gap - buffer implementation 2004 - 04 - 05
  • piece table 의: Data Structures for Text Sequences 1998 - 06 - 10
  • Ropes: An Alternative to Strings 1995-12

  • 현재 주요 세 가지 편집 방식 은 gap buffer, rope, piece table 이다.
    요즘 은 Atom 이 없어 졌어 요.
    지난번 에 나 를 흥분 시 킨 곳 은: The State of Atom 's Performance 였 다.2017 년 6 월 에 Atom 은 piece table 데이터 구 조 를 사 용 했 고 C + + 를 사용 하여 text buffer: Atom 's new concurrence - friendly buffer implementation 을 다시 실현 했다.vscode 보다 반년 빠 른 데 왜 이렇게 느 려 요?
    Atom 은 V8 의 사용자 정의 스냅 샷 (snapshot) 을 사용 하여 시작 성능 을 향상 시 키 고 성능 에 영향 을 주 는 jQuery 와 사용자 정의 element 를 삭제 합 니 다.V8 까지.
    Atom 은 DOM 렌 더 링 방식 도 업데이트 했다. A new approach to text rendering. 이 새로운 알고리즘 은 React 와 유사 한 vdom 을 포함 하고 issue 를 보면 큰 프로젝트 입 니 다. 100 개 에 가 까 운 task 를 포함 하고 있 습 니 다.
    일련의 최 적 화 를 거 쳐 공식 적 으로 말 했다.
    we made loading Atom almost 50% faster and snapshots were a crucial tool that enabled some otherwise impossible optimizations.
    우 리 는 Atom 을 50% 빨리 했 습 니 다. snapshot 의 공이 없어 서 는 안 됩 니 다.(PS: 저 는 가짜 Atom 을 사 용 했 을 거 예요)
    그러나 snapshot 은 확실히 V8 의 신기 이 고 Nodejs 도 Atom 의 성 과 를 보 았 으 며 2017 - 11 - 16 에 issue: speeding up Node. js startup using V8 snapshot · Issue \ # 17058 · nodejs / node 를 열 었 다.이것 은 제 이전 칼럼 에 소개 되 어 있 습 니 다. Node. js 새로운 계획: V8 snapshot 을 사용 하면 시작 속 도 를 8 배 올 립 니 다.
    최근 에 주목 한 Atom 은 아 톰 / xray 입 니 다.위 에서 도 관련 토론 이 있 는 것 을 알 고 있 습 니 다. 아 톰 이 개발 한 차세 대 편집기 (아 톰 을 차세 대 편집기 로 정의 한 것 이 아 닙 니까?)아마 '큰 사이즈 가 망 가 졌 으 니 작은 사이즈 로 다시 연습 하 자' 는 느낌 일 것 이다.
    배 울 점 은 text 처리 에 copy - on - write CRDT 를 사용 하 는 것 입 니 다.
    아 톰 을 계속 지 켜 봤 다 면 CRDT 에 대해 서 는 낯 설 지 않 았 을 것 이다.Atom 의 다 중 실시 간 공동 편집 플러그 인https://teletype.atom.io/ 사용 하 는 CRDT 입 니 다.
    CRDT 전 칭: Conflict - Free Replicated Data Types, 강제로 번역 하면 '충돌 없 이 데이터 형식 복사 가능' 입 니 다.
  • CRDT 논문: Convergent and Commutative Replicated Data Types 2011 - 01 - 13
  • 의 포괄 적 인 연구
    CAP 정리: 분포 식 시스템 에 서 는 일치 성 (Consistency), 가용성 (Availability), 파 티 션 용 착 성 (Partition tolerance) 세 가지 중 두 가지 만 동시에 만족 시 킬 수 있 습 니 다.
    많은 분포 식 시스템 이 C (일치 성) 를 버 렸 다. 특정한 시간 에 일치 하지 않 고 그 다음 에 시스템 이 최종 일치 성 을 만족 시 키 도록 요구 할 수 있다.이것 도 현재 많은 nosql 데이터베이스 가 추구 하 는 방식 이다.
    최종 일치 성 분포 식 시스템 에서 가장 기본 적 인 문 제 는 어떤 데이터 구 조 를 이용 하여 최종 일치 성 을 확보 해 야 하 는가 하 는 것 이다.정 답 은 CRDT.
  • atom/teletype-crdt

  • 이 글 은 단지 하나의 요강 일 뿐, 안의 모든 지식 점 은 3 박 3 일 동안 전개 할 수 있다.

    좋은 웹페이지 즐겨찾기