क्या रस्ट इतना भयानक है जितना इसे चित्रित किया गया है

कुछ समय पहले, मैंने अपने प्रोग्रामिंग अनुभव को विशेष रूप से C # में विविधता लाने की आवश्यकता को समझना शुरू किया। विभिन्न विकल्पों के कुछ अध्ययनों के बाद, जैसे हास्केल, स्काला, रस्ट और कुछ अन्य, पसंद बाद में गिर गई। समय के साथ, मैंने ध्यान देना शुरू किया कि रस्ट अधिक से अधिक केवल एक "सिस्टम भाषा" के रूप में विज्ञापित है, जो कि जटिल कंपाइलर और सुपर-लोड सिस्टम के लिए आवश्यक है, सुरक्षा और मल्टीथ्रेडिंग के लिए विशेष आवश्यकताओं के साथ, और गो / पायथन / जावा / ..., जबकि मैंने आनंद लिया और काफी सफलतापूर्वक इसका उपयोग मेरे सी # वर्कहॉर्स के प्रतिस्थापन के रूप में किया।



इस लेख में, मैं इस बारे में बात करना चाहता था कि मैं इस प्रवृत्ति को सामान्य रूप से हानिकारक क्यों मानता हूं, और क्यों रुस्त एक अच्छी सामान्य प्रयोजन वाली भाषा है, जिसका उपयोग किसी भी प्रकार की परियोजनाओं के लिए किया जा सकता है, किसी भी माइक्रोसिस्टर्स के साथ शुरू हो सकता है और दैनिक दिनचर्या स्क्रिप्टिंग के साथ समाप्त हो सकता है।


परिचय


क्यों, वास्तव में, एक नई भाषा सीखें, सभी अधिक जटिल? यह मुझे लगता है कि लेख का जवाब "मध्यस्थता पर विजय" सच्चाई के सबसे करीब है, अर्थात्:


हर कोई जानता है कि पूरे कार्यक्रम को मशीन भाषा में मैन्युअल रूप से लिखना एक गलती है। लेकिन उन्हें यह समझने की संभावना बहुत कम है कि एक अधिक सामान्य सिद्धांत है: यदि कई भाषाओं का विकल्प है, तो यह सबसे शक्तिशाली के अलावा किसी अन्य चीज पर प्रोग्राम करने के लिए गलत है, यदि विकल्प अन्य कारणों से प्रभावित नहीं है।

भाषा जितनी जटिल होती है, उसकी मदद से बनाए गए वाक्यांश उतने ही समृद्ध होते हैं, और बेहतर यह आवश्यक विषय क्षेत्र को व्यक्त कर सकता है। क्योंकि अवधारणाओं को आमतौर पर केवल एक बार अध्ययन किया जाता है, और बार-बार लागू किया जाता है, यह सभी प्रकार के डरावने शब्दों का अध्ययन करने के लिए अपने स्वयं के निवेश के दृष्टिकोण से बहुत अधिक लाभदायक है जैसे "मौद्रिक ट्रांसफार्मर" (और, अधिमानतः, उनका अर्थ), फिर अपनी मानसिक शक्ति को बचाने और उन्हें कुछ और खर्च करने के लिए। सुखद। और इसलिए विशेष रूप से "सरलीकृत" भाषा बनाने के लिए कुछ कंपनियों के रुझान को देखना बहुत दुखद है। नतीजतन, इन भाषाओं की शब्दावली बहुत छोटी है, और इसे सीखना मुश्किल नहीं है, लेकिन फिर "मेरे खुद के प्याज खरीदने के लिए" कार्यक्रमों को पढ़ना बहुत मुश्किल है, संभावित अस्पष्ट व्याख्याओं का उल्लेख नहीं करना।


मूल बातें


कैसे एक शुरुआत आमतौर पर एक प्रोग्रामिंग भाषा जानने के लिए मिलता है? वह सबसे लोकप्रिय भाषा की पुस्तक को गूगल करता है, उसे बाहर निकालता है, और पढ़ना शुरू करता है। एक नियम के रूप में, इसमें हैलोवर्ल्ड शामिल है, संकलक को स्थापित करने के निर्देश, और फिर एक क्रमिक जटिलता के साथ भाषा पर बुनियादी जानकारी। रैस्टा के मामले में, यह एक कमीने है , और पहला उदाहरण कंसोल से एक नंबर पढ़ रहा है और इसे स्क्रीन पर प्रदर्शित कर रहा है। हम इसे उसी C # में कैसे करेंगे? खैर, शायद कुछ ऐसा हो


var number = int.Parse(Console.ReadLine());
Console.WriteLine($"You guessed: {number}");

?


let mut guess = String::new();

io::stdin().read_line(&mut guess)
    .expect("Failed to read line");

let guess: u32 = guess.trim().parse()
    .expect("Please type a number!");

println!("You guessed: {}", guess);

, ( !), , .. " " "" .


:


let mut guess = String::new();
io::stdin().read_line(&mut guess)?;
let guess: u32 = guess.trim().parse()?;
println!("You guessed: {}", guess);

, , . , , . , , .


? - , , C# , , - .



.


fn search<F>(self, hash: u64, is_match: F, compare_hashes: bool)  
   -> RawEntryMut<'a, K, V, S>
  where for<'b> F: FnMut(&'b K) -> bool

, " ", " , ", " , GC ".


. , , . :


  • Each elided lifetime in input position becomes a distinct lifetime parameter.
  • If there is exactly one input lifetime position (elided or not), that lifetime is assigned to all elided output lifetimes.
  • If there are multiple input lifetime positions, but one of them is &self or &mut self, the lifetime of self is assigned to all elided output lifetimes.
  • Otherwise, it is an error to elide an output lifetime.

, , , , . . , -


struct Point(i32, i32);

impl Point {
    pub fn get_x(&self) -> &i32 {
        &self.0
    }

    pub fn get_y(&self) -> &i32 {
        &self.1
    }
}

, , .



  • GC . C# IDisposable, , , GC " ", . : , ( try-with-resources Java), , foreach … , , . , , . , DI ,
  • , 99% , .

, ( GC), ( ). : . , " ".



. , , :



. Rust 2018, . , . , .


pub struct Node {
    value: u64,
    next: Option<Box<Node>>,
    prev: Option<Box<Node>>,
}

, , .. Box<Node> , unique_ptr C++. , ,


:


pub struct Node {
    value: u64,
    next: Option<&Box<Node>>,
    prev: Option<&Box<Node>>,
}

( shared_ptr), . : - - . " , - ", dangling pointers . -, , , - " , , ".


, " ". , , , , ( Rc/Arc/Cell/RefCell), , .


: , . , , // . : GC , WeakReferences byte[] , , , . JS, , .


, " ", , . , , . , , . - , - . ownership'. , , , , .



. , , , .


,


error[E0382]: assign to part of moved value: `head`
  --> src\main.rs:23:5
   |
19 |         prev: Some(Box::new(head)),
   |                             ---- value moved here
...
23 |     head.next = Some(Box::new(next));
   |     ^^^^^^^^^ value partially assigned here after move
   |
   = note: move occurs because `head` has type `Node`, which does not implement the `Copy` trait

, , . , Copy , , - "", . , " ?".


, , compiler-driven development. , - , ", - . , . , ". , , :


fn foo<T: Copy>() {

}

fn bar<T>() {
    foo::<T>();
}

, :


error[E0277]: the trait bound `T: std::marker::Copy` is not satisfied
 --> src\main.rs:6:5
  |
6 |     foo::<T>();
  |     ^^^^^^^^ the trait `std::marker::Copy` is not implemented for `T`
  |
  = help: consider adding a `where T: std::marker::Copy` bound
note: required by `foo`
 --> src\main.rs:1:1
  |
1 | fn foo<T: Copy>() {
  | ^^^^^^^^^^^^^^^^^

error: aborting due to previous error

where T: std::marker::Copy , , , !


, IDE , - , , / , - , IDE. - , , CI - - - . - IDE , , , . .


- , . , . , , , . .


, , . , , . . FFI ++ , . , . C# , " null", " KeyNotFoundException", " ", .. JS ( ) , .


, == . , , , . , , buffer overflow . , ( ).



— , , . . -, , , , , , , . , , , , C#/Java/Go/… , . , — . , , — .


. , , , , , , ", , !". , , . , , ( Java/C#/..., ), ( /++), , .


, , , , . , " ". , , - .

Source: https://habr.com/ru/post/hi434200/


All Articles