Node에서 Rust로의 진출

왜 러스트인가?



몇 년 전에 나는 훌륭한 Programming Rust 책을 집어 들었습니다.

Rust 컴파일러가 메모리 안전을 강화하고 데이터 경합을 피하는 방법을 읽으면서 AHA가 생각났습니다! 다중 스레드 서버의 동기화 문제 없이 JavaScript 개발자가 동시성에 액세스할 수 있도록 하는 방법Node.js을 알게 된 순간입니다.

하지만 더 있습니다. Rust 프로그램은 런타임이 매우 적습니다. 가비지 컬렉터나 클래스 로더가 없습니다. 이로 인해 Rust는 임베디드 시스템이나 에지 컴퓨팅 플랫폼과 같은 제한된 환경에 이상적입니다.

이것 첫인상



이 글은 나의 첫 번째 Rust 크레이트 제작 경험을 다룹니다.

space 라이브러리는 숫자를 영어 단어로 변환하는 기능이 하나뿐인 작은 JavaScript 모듈인 을 복제하려고 시도합니다.

shortscale-rs은 정말 멋진 도구와 문서 모음을 생성했습니다.

시작하려면:
  • Rustshortscale를 설치합니다.
  • 새로운 업데이트가 있을 때마다 'rustup update'를 실행하십시오Rust ecosystem.

  • 이러한 단계는 Rust 빌드 도구인 using rustup 도 처리합니다.

    Rust release

    뱃짐 VS 코드



    기본 Rust 확장 대신 VS Code용을 설치하기 위해 Jason Williams의 을 따랐습니다. 디버깅을 위해 recommendations도 필요합니다.

    Rust Analyzer
    특히 VS Code 터미널에서 직접 doctest를 실행할 수 있는 기능이 마음에 듭니다.

    CodeLLDB 녹 문자열 및 str



    JavaScript에서 문자열을 작성하는 것은 간단합니다. +를 사용하여 임의의 문자열을 다른 문자열에 연결하십시오. 빈 문자열은 매우 간결한 논리를 작성하는 데 도움이 됩니다.

    의 아래 예는 빈 문자열을 무시하여 구분 기호 반복을 피한다는 점을 제외하면 기본 제공 falsy 과 같이 동작합니다.

    // concatenate array of strings, separated by sep, ignoring '' values
    function concat(strings, sep) {
      return strings.reduce((s1, s2) => s1 + (s1 && s2 ? sep : '') + s2, '')
    }
    


    여기 Rust에서 비슷한 일을 하는 제 shortscale.js가 있습니다.

    type Strvec = Vec<&'static str>;
    
    // concatenate 2 Strvec's, separated with "and" if both have length
    fn concat_and(v1: Strvec, v2: Strvec) -> Strvec {
        match (v1.len(), v2.len()) {
            (_, 0) => v1,
            (0, _) => v2,
            (_, _) => [v1, vec!["and"], v2].concat(),
        }
    }
    


    '왜 Strvec인가?'라고 물을 수도 있습니다. Rust에서 문자열 리터럴에 사용되는 기본 문자열 유형은 a Array.join 입니다. 내 첫 번째 생각은 shortscale-rs가 str 컬렉션을 조작해야 한다는 것이었습니다. 그래서 first attempt 연결을 사용하는 대신 str을 str에 넣었습니다.

    내가 좋아하는 Rust 언어 기능 중 하나인 우아한String 구문에 주목하세요. 컴파일러는 매치의 '팔'이 가능한 모든 입력을 포함하는지 확인합니다. 결과는 읽기 쉽고 간결합니다. '_'는 모든 값의 약어입니다.

    Performance does not matter,
    until it absolutely does.



    벡 벤치마크



    측정된match은 눈을 뜨게 했습니다! Rust에서는 호출당 ~4459ns, Node.js에서는 ~1342ns와 비교됩니다.

    performance

    shortscale                          251 ns/iter (+/- 18)
    shortscale_string_writer_no_alloc   191 ns/iter (+/- 11)
    shortscale_str_push                 247 ns/iter (+/- 22)
    shortscale_vec_push                 363 ns/iter (+/- 26)
    shortscale_display_no_alloc         498 ns/iter (+/- 21)
    shortscale_vec_concat              4459 ns/iter (+/- 344)
    shortscale_string_join             5549 ns/iter (+/- 378)
    


    shortscale_vec_concat

    shortscale                         1342 ns/iter
    


    분명히 Node.js의 v8 JavaScript 엔진은 문자열 조작을 효율적으로 만들기 위해 열심히 노력하고 있습니다.

    카고 벤치 학습 및 반복



    다음으로 시도한 것은 Vec 컬렉션을 간단한 문자열로 대체하여 Rust 프로그램의 각 함수에서 생성하고 반환하는 것이었습니다. 이것은 npm run bench 입니다. 벤치마크를 보면 성능이 훨씬 더 나빴음을 알 수 있습니다. 분명히 나는 ​​뭔가 잘못하고 있었다.

    로 빠르게 이동하여 새 문자열을 만들고 반환하는 함수를 호출하는 대신 미리 할당된 문자열을 변경합니다.

    The result is significantly faster than JavaScript.



    아직 배울 것이 많지만 이 연습은 Rust 개발과 Rust 프리미티브의 성능에 대한 직관을 구축하기 시작하는 좋은 방법이었습니다.

    좋은 웹페이지 즐겨찾기