Skip to content

Commit eb795f8

Browse files
sabiwarajosevalim
andauthored
Update getting started charlists to use ~c (#1702)
* Update getting started charlists to use ~c * Update getting-started/basic-types.markdown Co-authored-by: José Valim <[email protected]> --------- Co-authored-by: José Valim <[email protected]>
1 parent aafd60c commit eb795f8

File tree

4 files changed

+41
-21
lines changed

4 files changed

+41
-21
lines changed

getting-started/basic-types.markdown

+13-4
Original file line numberDiff line numberDiff line change
@@ -320,21 +320,28 @@ iex> hd([])
320320
** (ArgumentError) argument error
321321
```
322322
323-
Sometimes you will create a list and it will return a value in single quotes. For example:
323+
Sometimes you will create a list and it will return a quoted value preceded by `~c`. For example:
324324
325325
```elixir
326326
iex> [11, 12, 13]
327-
'\v\f\r'
327+
~c"\v\f\r"
328+
iex> [104, 101, 108, 108, 111]
329+
~c"hello"
330+
```
331+
332+
In Elixir versions before v1.15, this might be displayed as single quotes instead:
333+
334+
```elixir
328335
iex> [104, 101, 108, 108, 111]
329336
'hello'
330337
```
331338
332339
When Elixir sees a list of printable ASCII numbers, Elixir will print that as a charlist (literally a list of characters). Charlists are quite common when interfacing with existing Erlang code. Whenever you see a value in IEx and you are not quite sure what it is, you can use the `i/1` to retrieve information about it:
333340
334341
```elixir
335-
iex> i 'hello'
342+
iex> i ~c"hello"
336343
Term
337-
'hello'
344+
i ~c"hello"
338345
Data type
339346
List
340347
Description
@@ -352,6 +359,8 @@ Keep in mind single-quoted and double-quoted representations are not equivalent
352359
```elixir
353360
iex> 'hello' == "hello"
354361
false
362+
iex> 'hello' == ~c"hello"
363+
true
355364
```
356365
357366
Single quotes are charlists, double quotes are strings. We will talk more about them in the ["Binaries, strings and charlists"](/getting-started/binaries-strings-and-char-lists.html) chapter.

getting-started/binaries-strings-and-char-lists.markdown

+21-12
Original file line numberDiff line numberDiff line change
@@ -238,39 +238,48 @@ Our tour of our bitstrings, binaries, and strings is nearly complete, but we hav
238238

239239
**A charlist is a list of integers where all the integers are valid code points.** In practice, you will not come across them often, only in specific scenarios such as interfacing with older Erlang libraries that do not accept binaries as arguments.
240240

241-
Whereas double-quotes creates strings, single-quotes create charlist literals:
241+
```elixir
242+
iex> ~c"hello"
243+
~c"hello"
244+
iex> [?h, ?e, ?l, ?l, ?o]
245+
~c"hello"
246+
```
247+
248+
The `~c` sigil (we'll cover sigils later in the ["Sigils"](/getting-started/sigils.html) section)
249+
indicates the fact that we are dealing with a charlist and not a regular string.
250+
251+
Whereas double-quotes creates strings, single-quotes create charlist literals.
252+
Charlists used to be represented with single quotes in Elixir <1.15:
242253

243254
```elixir
244255
iex> 'hello'
245-
'hello'
246-
iex> [?h, ?e, ?l, ?l, ?o]
247-
'hello'
256+
~c"hello"
248257
```
249258

250259
The key takeaway is that `"hello"` is not the same as `'hello'`. Generally speaking, **double-quotes must always be used to represent strings in Elixir**. In any case, let's learn how charlists work.
251260

252261
Instead of containing bytes, a charlist contains integer code points. However, the list is only printed in single-quotes if all code points are within the ASCII range:
253262

254263
```elixir
255-
iex> 'hełło'
264+
iex> ~c"hełło"
256265
[104, 101, 322, 322, 111]
257-
iex> is_list('hełło')
266+
iex> is_list(~c"hełło")
258267
true
259268
```
260269

261270
Interpreting integers as code points may lead to some surprising behavior. For example, if you are storing a list of integers that happen to range between 0 and 127, by default IEx will interpret this as a charlist and it will display the corresponding ASCII characters.
262271

263272
```elixir
264273
iex> heartbeats_per_minute = [99, 97, 116]
265-
'cat'
274+
~c"cat"
266275
```
267276

268277
You can convert a charlist to a string and back by using the `to_string/1` and `to_charlist/1` functions:
269278

270279
```elixir
271280
iex> to_charlist("hełło")
272281
[104, 101, 322, 322, 111]
273-
iex> to_string('hełło')
282+
iex> to_string(~c"hełło")
274283
"hełło"
275284
iex> to_string(:hello)
276285
"hello"
@@ -283,14 +292,14 @@ Note that those functions are polymorphic - not only do they convert charlists t
283292
String (binary) concatenation uses the `<>` operator but charlists, being lists, use the list concatenation operator `++`:
284293

285294
```elixir
286-
iex> 'this ' <> 'fails'
287-
** (ArgumentError) expected binary argument in <> operator but got: 'this '
295+
iex> ~c"this " <> ~c"fails"
296+
** (ArgumentError) expected binary argument in <> operator but got: ~c"this "
288297
(elixir) lib/kernel.ex:1821: Kernel.wrap_concatenation/3
289298
(elixir) lib/kernel.ex:1808: Kernel.extract_concatenations/2
290299
(elixir) expanding macro: Kernel.<>/2
291300
iex:1: (file)
292-
iex> 'this ' ++ 'works'
293-
'this works'
301+
iex> ~c"this " ++ ~c"works"
302+
~c"this works"
294303
iex> "he" ++ "llo"
295304
** (ArgumentError) argument error
296305
:erlang.++("he", "llo")

getting-started/comprehensions.markdown

+1-1
Original file line numberDiff line numberDiff line change
@@ -44,7 +44,7 @@ Comprehensions discard all elements for which the filter expression returns `fal
4444
Comprehensions generally provide a much more concise representation than using the equivalent functions from the `Enum` and `Stream` modules. Furthermore, comprehensions also allow multiple generators and filters to be given. Here is an example that receives a list of directories and gets the size of each file in those directories:
4545

4646
```elixir
47-
dirs = ['/home/mikey', '/home/james']
47+
dirs = ["/home/mikey", "/home/james"]
4848

4949
for dir <- dirs,
5050
file <- File.ls!(dir),

getting-started/sigils.markdown

+6-4
Original file line numberDiff line numberDiff line change
@@ -65,11 +65,13 @@ iex> ~s(this is a string with "double" quotes, not 'single' ones)
6565

6666
### Char lists
6767

68-
The `~c` sigil is useful for generating char lists that contain single quotes:
68+
The `~c` sigil is the regular way to represent charlists.
6969

7070
```elixir
71-
iex> ~c(this is a char list containing 'single quotes')
72-
'this is a char list containing \'single quotes\''
71+
iex> [?c, ?a, ?t]
72+
~c"cat"
73+
iex> ~c(this is a char list containing "double quotes")
74+
~c"this is a char list containing \"double quotes\""
7375
```
7476

7577
### Word lists
@@ -214,7 +216,7 @@ iex> time_zone
214216
As hinted at the beginning of this chapter, sigils in Elixir are extensible. In fact, using the sigil `~r/foo/i` is equivalent to calling `sigil_r` with a binary and a char list as the argument:
215217

216218
```elixir
217-
iex> sigil_r(<<"foo">>, 'i')
219+
iex> sigil_r(<<"foo">>, ~c"i")
218220
~r"foo"i
219221
```
220222

0 commit comments

Comments
 (0)