├── .gitignore ├── README.md └── LICENSE /.gitignore: -------------------------------------------------------------------------------- 1 | .idea 2 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # A Java Devoloper's guide to Rust 2 | 3 | This is a list of stumbling blocks that I came across when I started doing Rust. 4 | I come from a Java background, so naturally that influenced my implicit expectations 5 | and assumptions. This document may or may not be helpful for people coming from 6 | other backgrounds - I wouldn't know :-). 7 | 8 | This document is just a list of insights that were not obvious for me. It is not 9 | intended as a comprehensive overview of the language or a tutorial. For that, there is 10 | [The Book](https://doc.rust-lang.org/book) and other excellent resources on the 11 | [Rust Homepage](https://rust-lang.org/learn) and elsewhere. 12 | 13 | I suggest you read this document before you start a tutorial, and come back to it 14 | when you feel the need. 15 | 16 | Anyway, here goes. 17 | 18 | ## General observations 19 | 20 | ### Same name, different concept 21 | 22 | There are things in Rust that have familiar sounding names but are just different 23 | enough to be confusing. You'd best forget that Java has things that are named the 24 | same, and learn the Rust features from the ground up. Most importantly, try **not** 25 | to use proven Java idioms with Rust features of the same name - they probably 26 | won't work or lead to pretty un-idiomatic Rust code. 27 | 28 | * Arrays (must have a length known at compile time) 29 | * Enums (something really different from Java enums) 30 | * Traits (look like Java interfaces but aren't really) 31 | 32 | There are detailed sections for these below. 33 | 34 | ### Compile time checking 35 | 36 | Rust is built around the concept of checking stuff at compile time. This can get 37 | in the way. Especially while you get started, this will probably often feel like 38 | "Leave me alone already, I know what I'm doing!". Well, that's intentional, and 39 | stringent compile time checks are at the heart of Rust's language design. 40 | 41 | If you write something you think is correct but the compiler disagrees, that 42 | is often a sign of a subtle bug. So learn to see compiler checks as your friend 43 | and not a necessary evil. 44 | 45 | Doing this will require you to unlearn some Java best practices and learn 46 | idiomatic ways to work with Rust and allow the compiler to do its checks. 47 | Acknowledge and embrace this - if you don't want that, Rust probably isn't the 48 | language for you. 49 | 50 | ### Standard library 51 | 52 | When I made my first steps with Rust, I tried to do things with 'just the language' 53 | without the standard library. That's what I usually like to do when learning a new 54 | language, I like to understand the language on its own, with its specific abstractions 55 | and sugar. 56 | 57 | Well, that didn't work for Rust, at least not the way I tried it. There are parts 58 | of the standard library that are necessary to do the most basic stuff: 59 | 60 | * `Vec` for dynamically-sized memory 61 | * `Box` (and pretty soon `Rc` / `Arc`) to get stuff onto the heap 62 | 63 | In hindsight, that is not a problem. It's just that other modern languages like 64 | Java (or C++, for that matter) support these things as part of their core 65 | language, and I struggled for a while trying to do these things "directly". 66 | 67 | My point is: While `Vec` and `Box` are part of the library, you will really 68 | really need them to take your first steps with Rust. There is no easy way 69 | to work with pointers or dynamically allocated lists without using "just 70 | language features". 71 | 72 | Embrace them and treat them as if they were part of the language core, at least until you know 73 | enough to understand how they are implemented. 74 | 75 | ## Features 76 | 77 | ### Arrays 78 | 79 | Arrays in Rust are something completely different from JVM arrays - try to ignore 80 | that they have the same name. 81 | 82 | Rust arrays are a continuous area of memory with a **size known at compile time**. 83 | An array of two bytes `[u8;2]` and an array of three bytes `[u8;3]` are totally 84 | different data types. They can not be assigned to each other, there is no common 85 | supertype - there is no way to use them interchangeably. 86 | 87 | That means there is **no way to create an array with a size known at runtime**. If 88 | you need something like that, using `Vec` from the standard library is the way to 89 | go - this is one more example that dynamically sized stuff is 'special' in Rust 90 | and less simple to do than statically sized stuff. 91 | 92 | And finally, arrays do **not** involve a pointer. An array can be allocated on the 93 | stack, and if an array is part of a struct, it is part of that struct's flat memory 94 | layout. Like any other data type, an array must reside behind a pointer in order 95 | to live on the heap. 96 | 97 | ### Slices 98 | 99 | Rust has *slices*, which are pointers to an array or part of it. They are 100 | "fat" pointers that contain length information which is checked at runtime and 101 | not part of the slice type. 102 | 103 | Slices have a type signature similar to arrays: `[u8;2]` is a byte array 104 | while `[u8]` is a slice of bytes. Though they look similar in code, they are 105 | very different beasts: 106 | 107 | * A slice **never owns** data. It is just a (borrowed) **view** to data owned 108 | e.g. by an array. 109 | * There is no way to allocate a slice directly. Slices are **not** a way to 110 | dynamically allocate memory. 111 | 112 | Slices are part of Rust's language core which may take some getting used to 113 | coming from Java. 114 | 115 | ### Enums and polymorphism 116 | 117 | Rust enums are designed so they can hold state, and **different state in different 118 | instances**. The following enum represents an IP address which can be either 119 | IP4 or IP6: 120 | 121 | ```rust 122 | enum InetAddress { 123 | V4(u8, u8, u8, u8), 124 | V6(String) 125 | } 126 | ``` 127 | 128 | This is completely different from Java: `V4` has different **instances** holding 129 | actual IP addresses. 130 | 131 | In Rust, this is a solution for many problems where you would use inheritance 132 | in Java. A Rust `enum` has a fixed number of variants that can each have different 133 | kinds of data, and functions can pattern match (Rust's more powerful equivalent 134 | of Java's `switch`) to handle different variants. 135 | 136 | Technically, this is not polymorphism but 137 | [Algebraic Types](https://en.wikipedia.org/wiki/Algebraic_data_type). But if 138 | feel like "I'd like some polymorphism here", you should start by trying to 139 | model that using enums. At least while you get started, so you get a feel 140 | for this language feature which Java does not have. 141 | 142 | If you are like me, this might raise a lot of concerns and leave you wondering 143 | "how do I do X". 144 | 145 | Well, firstly `trait`s do exist in Rust, it's just that they are not your first 146 | choice. But secondly, while I don't have all the answers yet, using enums for 147 | polymorphism works pretty well once I got used to it. Try to be open minded. 148 | 149 | ### Heap 150 | 151 | If you want to put stuff onto the heap, you one of the pointer structs (unless 152 | you go reeeeally low level using unsafe Rust - but if you know how to do that, 153 | you probably don't need this document any more). 154 | 155 | For your first steps, that means `Box` or `Arc`. 156 | 157 | `Arc` is roughly the equivalent of a Java object reference: You can have many 158 | `Arc` instances pointing to the same object in memory, and when the last of 159 | those is gone, the object is cleaned up ("dropped" in Rust terminology). 160 | When you need another reference to the same object, you `clone()` it. (Btw, 161 | "Arc" stands for "Atomic Reference Counter".) 162 | 163 | Many Rust tutorials start with `Box` as the first kind of pointer. A `Box` is 164 | the **single** reference to some object, and when the `Box` goes out of scope, 165 | the object is dropped. 166 | 167 | This is conceptually simpler than `Arc` and helps explain Rust's lifecycle 168 | concepts. `Box` is however very different from what you are used to in Java. 169 | 170 | The take-away is this: `Box` is great for learning lifecycle concepts, but if 171 | you hit a wall trying to do stuff that "should be simple", try `Arc` instead. 172 | And don't worry, this will feel natural pretty soon. 173 | 174 | ### Design for ownership and mutability 175 | 176 | One of the Rust's core rules basically says that **mutation requires exclusive 177 | access**. This is of course a simplification, and there are ways around this 178 | (`Cell`, atomic data types, ...), but the rule is pretty fundamental and is 179 | omnipresent in practice. 180 | 181 | It boils down to "shared state is read-only". You can work around this e.g. by 182 | adding a `Mutex` as a level of indirection and keep doing Java-style design, 183 | but that will likely feel weird and complex. 184 | 185 | In idiomatic Rust, you plan your abstractions and data structures around 186 | ownership and mutability. It may lead to splits between mutable and immutable 187 | data that you would combine into a single Java class. 188 | 189 | Question your Java-based intuition and experience for creating abstractions, 190 | and embrace Rust design as a new paradigm. That will probably feel weird at 191 | first (it did for me), but it will likely lead to new insights as well once 192 | you embrace it. 193 | 194 | ### Traits, Fat Pointers and Dynamically Sized Types 195 | 196 | In memory, a Rust `struct` consists only of its fields. There is no run-time 197 | type information that would allow reflection of any kind, there is no 198 | method table that would allow polymorphic invocation of method, there is 199 | nothing beyond the struct's raw data. 200 | 201 | For `enum`s, the compiler stores an additional byte or so to determine which 202 | of the enum's variants the data represents. But even for enums, Rust stores 203 | just enough to determine a given enum's variant and no more. 204 | 205 | This works great when the compiler knows the data's concrete type. Which is 206 | the normal case in Rust. 207 | 208 | Obviously, this does not allow any "real" polymorphism however, where the caller 209 | only knows that a given objects implements a certain `trait` and calls 210 | one of the trait's methods. 211 | 212 | #### Polymorphism via pointers 213 | 214 | Rust does allow pointers with a `trait` as their static type. And you can 215 | invoke methods on these pointers. There is e.g. the `FnOnce` trait which 216 | is implemented by all closures: 217 | 218 | ```rust 219 | let f = || { println!("Hi"); }; 220 | let fn_ptr: Box = Box::new(f); 221 | ``` 222 | 223 | Rust does this by using a trick under the hood: a pointer to a trait is stored 224 | as two pointers internally, one of them to the object and one to a virtual 225 | method table. These pointers are called "fat" pointers, and you should usually 226 | not have to worry about them. 227 | 228 | #### Dynamically Sized Types 229 | 230 | That is, as long as you work with them through pointers. When you start passing 231 | objects around "directly" via a `trait` or have a field in a struct that has 232 | a `trait` as its type, you will see compiler errors saying that the type's size 233 | is not known at compile time. 234 | 235 | That is because Rust can not know at compile time how much memory to allocate 236 | for data based on a trait - and for many things the compiler needs to do just 237 | that. 238 | 239 | #### The take-away 240 | 241 | Rust sometimes exposes you as a programmer to memory layout issues. Rust 242 | focuses on doing stuff at compile time, therefore some stuff requires data 243 | size to be known at compile time. 244 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Apache License 2 | Version 2.0, January 2004 3 | http://www.apache.org/licenses/ 4 | 5 | TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION 6 | 7 | 1. Definitions. 8 | 9 | "License" shall mean the terms and conditions for use, reproduction, 10 | and distribution as defined by Sections 1 through 9 of this document. 11 | 12 | "Licensor" shall mean the copyright owner or entity authorized by 13 | the copyright owner that is granting the License. 14 | 15 | "Legal Entity" shall mean the union of the acting entity and all 16 | other entities that control, are controlled by, or are under common 17 | control with that entity. For the purposes of this definition, 18 | "control" means (i) the power, direct or indirect, to cause the 19 | direction or management of such entity, whether by contract or 20 | otherwise, or (ii) ownership of fifty percent (50%) or more of the 21 | outstanding shares, or (iii) beneficial ownership of such entity. 22 | 23 | "You" (or "Your") shall mean an individual or Legal Entity 24 | exercising permissions granted by this License. 25 | 26 | "Source" form shall mean the preferred form for making modifications, 27 | including but not limited to software source code, documentation 28 | source, and configuration files. 29 | 30 | "Object" form shall mean any form resulting from mechanical 31 | transformation or translation of a Source form, including but 32 | not limited to compiled object code, generated documentation, 33 | and conversions to other media types. 34 | 35 | "Work" shall mean the work of authorship, whether in Source or 36 | Object form, made available under the License, as indicated by a 37 | copyright notice that is included in or attached to the work 38 | (an example is provided in the Appendix below). 39 | 40 | "Derivative Works" shall mean any work, whether in Source or Object 41 | form, that is based on (or derived from) the Work and for which the 42 | editorial revisions, annotations, elaborations, or other modifications 43 | represent, as a whole, an original work of authorship. For the purposes 44 | of this License, Derivative Works shall not include works that remain 45 | separable from, or merely link (or bind by name) to the interfaces of, 46 | the Work and Derivative Works thereof. 47 | 48 | "Contribution" shall mean any work of authorship, including 49 | the original version of the Work and any modifications or additions 50 | to that Work or Derivative Works thereof, that is intentionally 51 | submitted to Licensor for inclusion in the Work by the copyright owner 52 | or by an individual or Legal Entity authorized to submit on behalf of 53 | the copyright owner. For the purposes of this definition, "submitted" 54 | means any form of electronic, verbal, or written communication sent 55 | to the Licensor or its representatives, including but not limited to 56 | communication on electronic mailing lists, source code control systems, 57 | and issue tracking systems that are managed by, or on behalf of, the 58 | Licensor for the purpose of discussing and improving the Work, but 59 | excluding communication that is conspicuously marked or otherwise 60 | designated in writing by the copyright owner as "Not a Contribution." 61 | 62 | "Contributor" shall mean Licensor and any individual or Legal Entity 63 | on behalf of whom a Contribution has been received by Licensor and 64 | subsequently incorporated within the Work. 65 | 66 | 2. Grant of Copyright License. Subject to the terms and conditions of 67 | this License, each Contributor hereby grants to You a perpetual, 68 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 69 | copyright license to reproduce, prepare Derivative Works of, 70 | publicly display, publicly perform, sublicense, and distribute the 71 | Work and such Derivative Works in Source or Object form. 72 | 73 | 3. Grant of Patent License. Subject to the terms and conditions of 74 | this License, each Contributor hereby grants to You a perpetual, 75 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 76 | (except as stated in this section) patent license to make, have made, 77 | use, offer to sell, sell, import, and otherwise transfer the Work, 78 | where such license applies only to those patent claims licensable 79 | by such Contributor that are necessarily infringed by their 80 | Contribution(s) alone or by combination of their Contribution(s) 81 | with the Work to which such Contribution(s) was submitted. If You 82 | institute patent litigation against any entity (including a 83 | cross-claim or counterclaim in a lawsuit) alleging that the Work 84 | or a Contribution incorporated within the Work constitutes direct 85 | or contributory patent infringement, then any patent licenses 86 | granted to You under this License for that Work shall terminate 87 | as of the date such litigation is filed. 88 | 89 | 4. Redistribution. You may reproduce and distribute copies of the 90 | Work or Derivative Works thereof in any medium, with or without 91 | modifications, and in Source or Object form, provided that You 92 | meet the following conditions: 93 | 94 | (a) You must give any other recipients of the Work or 95 | Derivative Works a copy of this License; and 96 | 97 | (b) You must cause any modified files to carry prominent notices 98 | stating that You changed the files; and 99 | 100 | (c) You must retain, in the Source form of any Derivative Works 101 | that You distribute, all copyright, patent, trademark, and 102 | attribution notices from the Source form of the Work, 103 | excluding those notices that do not pertain to any part of 104 | the Derivative Works; and 105 | 106 | (d) If the Work includes a "NOTICE" text file as part of its 107 | distribution, then any Derivative Works that You distribute must 108 | include a readable copy of the attribution notices contained 109 | within such NOTICE file, excluding those notices that do not 110 | pertain to any part of the Derivative Works, in at least one 111 | of the following places: within a NOTICE text file distributed 112 | as part of the Derivative Works; within the Source form or 113 | documentation, if provided along with the Derivative Works; or, 114 | within a display generated by the Derivative Works, if and 115 | wherever such third-party notices normally appear. The contents 116 | of the NOTICE file are for informational purposes only and 117 | do not modify the License. You may add Your own attribution 118 | notices within Derivative Works that You distribute, alongside 119 | or as an addendum to the NOTICE text from the Work, provided 120 | that such additional attribution notices cannot be construed 121 | as modifying the License. 122 | 123 | You may add Your own copyright statement to Your modifications and 124 | may provide additional or different license terms and conditions 125 | for use, reproduction, or distribution of Your modifications, or 126 | for any such Derivative Works as a whole, provided Your use, 127 | reproduction, and distribution of the Work otherwise complies with 128 | the conditions stated in this License. 129 | 130 | 5. Submission of Contributions. Unless You explicitly state otherwise, 131 | any Contribution intentionally submitted for inclusion in the Work 132 | by You to the Licensor shall be under the terms and conditions of 133 | this License, without any additional terms or conditions. 134 | Notwithstanding the above, nothing herein shall supersede or modify 135 | the terms of any separate license agreement you may have executed 136 | with Licensor regarding such Contributions. 137 | 138 | 6. Trademarks. This License does not grant permission to use the trade 139 | names, trademarks, service marks, or product names of the Licensor, 140 | except as required for reasonable and customary use in describing the 141 | origin of the Work and reproducing the content of the NOTICE file. 142 | 143 | 7. Disclaimer of Warranty. Unless required by applicable law or 144 | agreed to in writing, Licensor provides the Work (and each 145 | Contributor provides its Contributions) on an "AS IS" BASIS, 146 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or 147 | implied, including, without limitation, any warranties or conditions 148 | of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A 149 | PARTICULAR PURPOSE. You are solely responsible for determining the 150 | appropriateness of using or redistributing the Work and assume any 151 | risks associated with Your exercise of permissions under this License. 152 | 153 | 8. Limitation of Liability. In no event and under no legal theory, 154 | whether in tort (including negligence), contract, or otherwise, 155 | unless required by applicable law (such as deliberate and grossly 156 | negligent acts) or agreed to in writing, shall any Contributor be 157 | liable to You for damages, including any direct, indirect, special, 158 | incidental, or consequential damages of any character arising as a 159 | result of this License or out of the use or inability to use the 160 | Work (including but not limited to damages for loss of goodwill, 161 | work stoppage, computer failure or malfunction, or any and all 162 | other commercial damages or losses), even if such Contributor 163 | has been advised of the possibility of such damages. 164 | 165 | 9. Accepting Warranty or Additional Liability. While redistributing 166 | the Work or Derivative Works thereof, You may choose to offer, 167 | and charge a fee for, acceptance of support, warranty, indemnity, 168 | or other liability obligations and/or rights consistent with this 169 | License. However, in accepting such obligations, You may act only 170 | on Your own behalf and on Your sole responsibility, not on behalf 171 | of any other Contributor, and only if You agree to indemnify, 172 | defend, and hold each Contributor harmless for any liability 173 | incurred by, or claims asserted against, such Contributor by reason 174 | of your accepting any such warranty or additional liability. 175 | 176 | END OF TERMS AND CONDITIONS 177 | 178 | APPENDIX: How to apply the Apache License to your work. 179 | 180 | To apply the Apache License to your work, attach the following 181 | boilerplate notice, with the fields enclosed by brackets "[]" 182 | replaced with your own identifying information. (Don't include 183 | the brackets!) The text should be enclosed in the appropriate 184 | comment syntax for the file format. We also recommend that a 185 | file or class name and description of purpose be included on the 186 | same "printed page" as the copyright notice for easier 187 | identification within third-party archives. 188 | 189 | Copyright [yyyy] [name of copyright owner] 190 | 191 | Licensed under the Apache License, Version 2.0 (the "License"); 192 | you may not use this file except in compliance with the License. 193 | You may obtain a copy of the License at 194 | 195 | http://www.apache.org/licenses/LICENSE-2.0 196 | 197 | Unless required by applicable law or agreed to in writing, software 198 | distributed under the License is distributed on an "AS IS" BASIS, 199 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 200 | See the License for the specific language governing permissions and 201 | limitations under the License. 202 | --------------------------------------------------------------------------------