# Getting Started · The Julia Language
Source: https://docs.julialang.org/en/v1/manual/getting-started/


# [Getting Started](#man-getting-started)
Julia installation is straightforward, whether using precompiled binaries or compiling from source. Download and install Julia by following the instructions at <https://julialang.org/install/>.
If you are coming to Julia from one of the following languages, then you should start by reading the section on noteworthy differences from [MATLAB](../noteworthy-differences/#Noteworthy-differences-from-MATLAB), [R](../noteworthy-differences/#Noteworthy-differences-from-R), [Python](../noteworthy-differences/#Noteworthy-differences-from-Python), [C/C++](../noteworthy-differences/#Noteworthy-differences-from-C/C) or [Common Lisp](../noteworthy-differences/#Noteworthy-differences-from-Common-Lisp). This will help you avoid some common pitfalls since Julia differs from those languages in many subtle ways.
The easiest way to learn and experiment with Julia is by starting an interactive session (also known as a read-eval-print loop or "REPL") by double-clicking the Julia executable or running `julia` from the command line:
```julia
$ julia

               _
   _       _ _(_)_     |  Documentation: https://docs.julialang.org
  (_)     | (_) (_)    |
   _ _   _| |_  __ _   |  Type "?" for help, "]?" for Pkg help.
  | | | | | | |/ _` |  |
  | | |_| | | | (_| |  |  Version 1.11.6 (2025-07-09)
 _/ |\__'_|_|_|\__'_|  |  Official https://julialang.org/ release
|__/                   |

julia> 1 + 2
3

julia> ans
3
```


# [Getting Started](#man-getting-started)
To exit the interactive session, type `CTRL-D` (press the Control/`^` key together with the `d` key), or type `exit()`. When run in interactive mode, `julia` displays a banner and prompts the user for input. Once the user has entered a complete expression, such as `1 + 2`, and hits enter, the interactive session evaluates the expression and shows its value. If an expression is entered into an interactive session with a trailing semicolon, its value is not shown. The variable `ans` is bound to the value of the last evaluated expression whether it is shown or not. The `ans` variable is only bound in interactive sessions, not when Julia code is run in other ways.
To evaluate expressions written in a source file `file.jl`, write `include("file.jl")`.
To run code in a file non-interactively, you can give it as the first argument to the `julia` command:
```julia
$ julia script.jl
```
You can pass additional arguments to Julia, and to your program `script.jl`. A detailed list of all the available options can be found under [Command-line Interface](../command-line-interface/#cli).


## [Resources](#Resources)
A curated list of useful learning resources to help new users get started can be found on the [learning](https://julialang.org/learning/) page of the main Julia website.
You can use the REPL as a learning resource by switching into the help mode. Switch to help mode by pressing `?` at an empty `julia>` prompt, before typing anything else. Typing a keyword in help mode will fetch the documentation for it, along with examples. Similarly for most functions or other objects you might encounter!
```julia
help?> begin
search: begin disable_sigint reenable_sigint

  begin

  begin...end denotes a block of code.
```
If you already know Julia a bit, you might want to peek ahead at [Performance Tips](../performance-tips/#man-performance-tips) and [Workflow Tips](../workflow-tips/#man-workflow-tips).
------------------------------------------------------------------------


# Installation · The Julia Language
Source: https://docs.julialang.org/en/v1/manual/installation/


# [Installation](#man-installation)
There are many ways to install Julia. The following sections highlight the recommended method for each of the main supported platforms, and then present alternative ways that might be useful in specialized situations.
The current installation recommendation is a solution based on Juliaup. If you installed Julia previously with a method that is *not* based on Juliaup and want to switch your system to an installation that is based on Juliaup, we recommend that you uninstall all previous Julia versions, ensure that you remove anything Julia related from your `PATH` variable and then install Julia with one of the methods described below.


## [Windows](#Windows)
On Windows Julia can be installed directly from the Windows store [here](https://www.microsoft.com/store/apps/9NJNWW8PVKMN). One can also install exactly the same version by executing
```julia
winget install julia -s msstore
```
in any shell.


## [Mac and Linux](#Mac-and-Linux)
Julia can be installed on Linux or Mac by executing
```julia
curl -fsSL https://install.julialang.org | sh
```
in a shell.


### [Command line arguments](#Command-line-arguments)
One can pass various command line arguments to the Julia installer. The syntax for installer arguments is
```bash
curl -fsSL https://install.julialang.org | sh -s -- <ARGS>
```
Here `<ARGS>` should be replaced with one or more of the following arguments:
-   `--yes` (or `-y`): Run the installer in a non-interactive mode. All configuration values use their default or a value supplied as a command line argument.
-   `--default-channel=<NAME>`: Configure the default Juliaup channel. For example `--default-channel lts` would install the `lts` channel and configure it as the default.
-   `--add-to-path=<yes|no>`: Configure whether Julia should be added to the `PATH` environment variable. Valid values are `yes` (default) and `no`.
-   `--background-selfupdate=<SECONDS>`: Configure an optional CRON job that auto-updates Juliaup if `<SECONDS>` has a value larger than 0. The actual value controls how often the CRON job will run to check for a new Juliaup version in seconds. The default value is 0, i.e. no CRON job will be created.
-   `--startup-selfupdate=<MINUTES>`: Configure how often Julia will check for new versions of Juliaup when Julia is started. The default is every 1440 minutes.
-   `-p=<PATH>` (or `--path`): Configure where the Julia and Juliaup binaries are installed. The default is `~/.juliaup`.


## [Alternative installation methods](#Alternative-installation-methods)
Note that we recommend the following methods *only* if none of the installation methods described above work for your system.
Some of the installation methods described below recommend installing a package called `juliaup`. Note that this nevertheless installs a fully functional Julia system, not just Juliaup.


### [App Installer (Windows)](#App-Installer-(Windows))
If the Windows Store is blocked on a system, we have an alternative [MSIX App Installer](https://learn.microsoft.com/en-us/windows/msix/app-installer/app-installer-file-overview) based setup. To use the App Installer version, download [this](https://install.julialang.org/Julia.appinstaller) file and open it by double clicking on it.


### [MSI Installer (Windows)](#MSI-Installer-(Windows))
If neither the Windows Store nor the App Installer version work on your Windows system, you can also use a MSI based installer. Note that this installation methods comes with serious limitations and is generally not recommended unless no other method works. For example, there is no automatic update mechanism for Juliaup with this installation method. The 64 bit version of the MSI installer can be downloaded from [here](https://install.julialang.org/Julia-x64.msi) and the 32 bit version from [here](https://install.julialang.org/Julia-x86.msi).
By default the install will be a per-user install that does not require elevation. You can also do a system install by running the following command from a shell:
```julia
msiexec /i <PATH_TO_JULIA_MSI> ALLUSERS=1
```


### [Homebrew](https://brew.sh) (Mac and Linux)
On systems with brew, you can install Julia by running
```julia
brew install juliaup
```
in a shell. Note that you will have to update Juliaup with standard brew commands.


### [Arch Linux - AUR](https://aur.archlinux.org/packages/juliaup/) (Linux)
On Arch Linux, Juliaup is available [in the Arch User Repository (AUR)](https://aur.archlinux.org/packages/juliaup/).


### [openSUSE Tumbleweed](https://get.opensuse.org/tumbleweed/) (Linux)
On openSUSE Tumbleweed, you can install Julia by running
```sh
zypper install juliaup
```
in a shell with root privileges.


### [cargo](https://crates.io/crates/juliaup/) (Windows, Mac and Linux)
To install Julia via Rust's cargo, run:
```sh
cargo install juliaup
```
------------------------------------------------------------------------


# Variables · The Julia Language
Source: https://docs.julialang.org/en/v1/manual/variables/


# [Variables](#man-variables)
A variable, in Julia, is a name associated (or bound) to a value. It's useful when you want to store a value (that you obtained after some math, for example) for later use. For example:
```julia-repl
# Assign the value 10 to the variable x
julia> x = 10
10

# Doing math with x's value
julia> x + 1
11

# Reassign x's value
julia> x = 1 + 1
2

# You can assign values of other types, like strings of text
julia> x = "Hello World!"
"Hello World!"
```
Julia provides an extremely flexible system for naming variables. Variable names are case-sensitive, and have no semantic meaning (that is, the language will not treat variables differently based on their names).
```julia-repl
julia> x = 1.0
1.0

julia> y = -3
-3

julia> Z = "My string"
"My string"

julia> customary_phrase = "Hello world!"
"Hello world!"

julia> UniversalDeclarationOfHumanRightsStart = "人人生而自由，在尊严和权利上一律平等。"
"人人生而自由，在尊严和权利上一律平等。"
```
Unicode names (in UTF-8 encoding) are allowed:
```julia-repl
julia> δ = 0.00001
1.0e-5

julia> 안녕하세요 = "Hello"
"Hello"
```
In the Julia REPL and several other Julia editing environments, you can type many Unicode math symbols by typing the backslashed LaTeX symbol name followed by tab. For example, the variable name `δ` can be entered by typing `\delta`-*tab*, or even `α̂⁽²⁾` by `\alpha`-*tab*-`\hat`- *tab*-`\^(2)`-*tab*. (If you find a symbol somewhere, e.g. in someone else's code, that you don't know how to type, the REPL help will tell you: just type `?` and then paste the symbol.)


# [Variables](#man-variables)
Julia will even let you shadow existing exported constants and functions with local ones (although this is not recommended to avoid potential confusions):
```julia-repl
julia> pi = 3
3

julia> pi
3

julia> sqrt = 4
4

julia> length() = 5
length (generic function with 1 method)

julia> Base.length
length (generic function with 79 methods)
```
However, if you try to redefine a built-in constant or function already in use, Julia will give you an error:
```julia-repl
julia> pi
π = 3.1415926535897...

julia> pi = 3
ERROR: cannot assign a value to imported variable Base.pi from module Main

julia> sqrt(100)
10.0

julia> sqrt = 4
ERROR: cannot assign a value to imported variable Base.sqrt from module Main
```


## [Allowed Variable Names](#man-allowed-variable-names)
Variable names must begin with a letter (A-Z or a-z), underscore, or a subset of Unicode code points greater than 00A0; in particular, [Unicode character categories](https://www.fileformat.info/info/unicode/category/index.htm) Lu/Ll/Lt/Lm/Lo/Nl (letters), Sc/So (currency and other symbols), and a few other letter-like characters (e.g. a subset of the Sm math symbols) are allowed. Subsequent characters may also include ! and digits (0-9 and other characters in categories Nd/No), as well as other Unicode code points: diacritics and other modifying marks (categories Mn/Mc/Me/Sk), some punctuation connectors (category Pc), primes, and a few other characters.
Operators like `+` are also valid identifiers, but are parsed specially. In some contexts, operators can be used just like variables; for example `(+)` refers to the addition function, and `(+) = f` will reassign it. Most of the Unicode infix operators (in category Sm), such as `⊕`, are parsed as infix operators and are available for user-defined methods (e.g. you can use `const ⊗ = kron` to define `⊗` as an infix Kronecker product). Operators can also be suffixed with modifying marks, primes, and sub/superscripts, e.g. `+̂ₐ″` is parsed as an infix operator with the same precedence as `+`. A space is required between an operator that ends with a subscript/superscript letter and a subsequent variable name. For example, if `+ᵃ` is an operator, then `+ᵃx` must be written as `+ᵃ x` to distinguish it from `+ ᵃx` where `ᵃx` is the variable name.


## [Allowed Variable Names](#man-allowed-variable-names)
A particular class of variable names is one that contains only underscores. These identifiers are write-only. I.e. they can only be assigned values, which are immediately discarded, and their values cannot be used in any way.
```julia-repl
julia> x, ___ = size([2 2; 1 1])
(2, 2)

julia> y = ___
ERROR: syntax: all-underscore identifiers are write-only and their values cannot be used in expressions

julia> println(___)
ERROR: syntax: all-underscore identifiers are write-only and their values cannot be used in expressions
```
The only explicitly disallowed names for variables are the names of the built-in [Keywords](../../base/base/#Keywords):
```julia-repl
julia> else = false
ERROR: syntax: unexpected "else"

julia> try = "No"
ERROR: syntax: unexpected "="
```


## [Allowed Variable Names](#man-allowed-variable-names)
Some Unicode characters are considered to be equivalent in identifiers. Different ways of entering Unicode combining characters (e.g., accents) are treated as equivalent (specifically, Julia identifiers are [NFC](https://en.wikipedia.org/wiki/Unicode_equivalence). Julia also includes a few non-standard equivalences for characters that are visually similar and are easily entered by some input methods. The Unicode characters `ɛ` (U+025B: Latin small letter open e) and `µ` (U+00B5: micro sign) are treated as equivalent to the corresponding Greek letters. The middle dot `·` (U+00B7) and the Greek [interpunct](https://en.wikipedia.org/wiki/Interpunct) `·` (U+0387) are both treated as the mathematical dot operator `⋅` (U+22C5). The minus sign `−` (U+2212) is treated as equivalent to the hyphen-minus sign `-` (U+002D).


## [Assignment expressions and assignment versus mutation](#man-assignment-expressions)
An assignment `variable = value` "binds" the name `variable` to the `value` computed on the right-hand side, and the whole assignment is treated by Julia as an expression equal to the right-hand-side `value`. This means that assignments can be *chained* (the same `value` assigned to multiple variables with `variable1 = variable2 = value`) or used in other expressions, and is also why their result is shown in the REPL as the value of the right-hand side. (In general, the REPL displays the value of whatever expression you evaluate.) For example, here the value `4` of `b = 2+2` is used in another arithmetic operation and assignment:
```julia-repl
julia> a = (b = 2+2) + 3
7

julia> a
7

julia> b
4
```
A common confusion is the distinction between *assignment* (giving a new "name" to a value) and *mutation* (changing a value). If you run `a = 2` followed by `a = 3`, you have changed the "name" `a` to refer to a new value `3` … you haven't changed the number `2`, so `2+2` will still give `4` and not `6`! This distinction becomes more clear when dealing with *mutable* types like [arrays](../../base/arrays/#lib-arrays), whose contents *can* be changed:
```julia-repl
julia> a = [1,2,3] # an array of 3 integers
3-element Vector{Int64}:
 1
 2
 3

julia> b = a   # both b and a are names for the same array!
3-element Vector{Int64}:
 1
 2
 3
```


## [Assignment expressions and assignment versus mutation](#man-assignment-expressions)
Here, the line `b = a` does *not* make a copy of the array `a`, it simply binds the name `b` to the *same* array `a`: both `b` and `a` "point" to one array `[1,2,3]` in memory. In contrast, an assignment `a[i] = value` *changes* the *contents* of the array, and the modified array will be visible through both the names `a` and `b`:
```julia-repl
julia> a[1] = 42     # change the first element
42

julia> a = 3.14159   # a is now the name of a different object
3.14159

julia> b   # b refers to the original array object, which has been mutated
3-element Vector{Int64}:
 42
  2
  3
```
That is, `a[i] = value` (an alias for [`setindex!`](../../base/collections/#Base.setindex!)) *mutates* an existing array object in memory, accessible via either `a` or `b`. Subsequently setting `a = 3.14159` does not change this array, it simply binds `a` to a different object; the array is still accessible via `b`. Another common syntax to mutate an existing object is `a.field = value` (an alias for [`setproperty!`](../../base/base/#Base.setproperty!)), which can be used to change a [`mutable struct`](../../base/base/#mutable%20struct). There is also mutation via dot assignment, for example `b .= 5:7` (which mutates our array `b` in-place to contain `[5,6,7]`), as part of Julia's [vectorized "dot" syntax](../mathematical-operations/#man-dot-operators).


## [Assignment expressions and assignment versus mutation](#man-assignment-expressions)
When you call a [function](../functions/#man-functions) in Julia, it behaves as if you *assigned* the argument values to new variable names corresponding to the function arguments, as discussed in [Argument-Passing Behavior](../functions/#man-argument-passing). (By [convention](../../base/punctuation/#man-punctuation), functions that mutate one or more of their arguments have names ending with `!`.)


## [Stylistic Conventions](#Stylistic-Conventions)
While Julia imposes few restrictions on valid names, it has become useful to adopt the following conventions:
-   Names of variables are in lower case.
-   Word separation can be indicated by underscores (`'_'`), but use of underscores is discouraged unless the name would be hard to read otherwise.
-   Names of `Type`s and `Module`s begin with a capital letter and word separation is shown with upper camel case instead of underscores.
-   Names of `function`s and `macro`s are in lower case, without underscores.
-   Functions that write to their arguments have names that end in `!`. These are sometimes called "mutating" or "in-place" functions because they are intended to produce changes in their arguments after the function is called, not just return a value.
For more information about stylistic conventions, see the [Style Guide](../style-guide/#Style-Guide).
------------------------------------------------------------------------


# Integers and Floating-Point Numbers · The Julia Language
Source: https://docs.julialang.org/en/v1/manual/integers-and-floating-point-numbers/


# [Integers and Floating-Point Numbers](#Integers-and-Floating-Point-Numbers)
Integers and floating-point values are the basic building blocks of arithmetic and computation. Built-in representations of such values are called numeric primitives, while representations of integers and floating-point numbers as immediate values in code are known as numeric literals. For example, `1` is an integer literal, while `1.0` is a floating-point literal; their binary in-memory representations as objects are numeric primitives.
Julia provides a broad range of primitive numeric types, and a full complement of arithmetic and bitwise operators as well as standard mathematical functions are defined over them. These map directly onto numeric types and operations that are natively supported on modern computers, thus allowing Julia to take full advantage of computational resources. Additionally, Julia provides software support for [Arbitrary Precision Arithmetic](#Arbitrary-Precision-Arithmetic), which can handle operations on numeric values that cannot be represented effectively in native hardware representations, but at the cost of relatively slower performance.
The following are Julia's primitive numeric types:
-   **Integer types:**


# [Integers and Floating-Point Numbers](#Integers-and-Floating-Point-Numbers)
| Type                                          | Signed? | Number of bits | Smallest value | Largest value |
|:----------------------------------------------|:--------|:---------------|:---------------|:--------------|
| [`Int8`](../../base/numbers/#Core.Int8)       | ✓       | 8              | -2^7           | 2^7 - 1       |
| [`UInt8`](../../base/numbers/#Core.UInt8)     |         | 8              | 0              | 2^8 - 1       |
| [`Int16`](../../base/numbers/#Core.Int16)     | ✓       | 16             | -2^15          | 2^15 - 1      |
| [`UInt16`](../../base/numbers/#Core.UInt16)   |         | 16             | 0              | 2^16 - 1      |
| [`Int32`](../../base/numbers/#Core.Int32)     | ✓       | 32             | -2^31          | 2^31 - 1      |
| [`UInt32`](../../base/numbers/#Core.UInt32)   |         | 32             | 0              | 2^32 - 1      |
| [`Int64`](../../base/numbers/#Core.Int64)     | ✓       | 64             | -2^63          | 2^63 - 1      |
| [`UInt64`](../../base/numbers/#Core.UInt64)   |         | 64             | 0              | 2^64 - 1      |
| [`Int128`](../../base/numbers/#Core.Int128)   | ✓       | 128            | -2^127         | 2^127 - 1     |
| [`UInt128`](../../base/numbers/#Core.UInt128) |         | 128            | 0              | 2^128 - 1     |
| [`Bool`](../../base/numbers/#Core.Bool)       | N/A     | 8              | `false` (0)    | `true` (1)    |
-   **Floating-point types:**


# [Integers and Floating-Point Numbers](#Integers-and-Floating-Point-Numbers)
| Type                                          | Precision                                                                      | Number of bits |
|:----------------------------------------------|:-------------------------------------------------------------------------------|:---------------|
| [`Float16`](../../base/numbers/#Core.Float16) | [half](https://en.wikipedia.org/wiki/Half-precision_floating-point_format)     | 16             |
| [`Float32`](../../base/numbers/#Core.Float32) | [single](https://en.wikipedia.org/wiki/Single_precision_floating-point_format) | 32             |
| [`Float64`](../../base/numbers/#Core.Float64) | [double](https://en.wikipedia.org/wiki/Double_precision_floating-point_format) | 64             |
Additionally, full support for [Complex and Rational Numbers](../complex-and-rational-numbers/#Complex-and-Rational-Numbers) is built on top of these primitive numeric types. All numeric types interoperate naturally without explicit casting, thanks to a flexible, user-extensible [type promotion system](../conversion-and-promotion/#conversion-and-promotion).


## [Integers](#Integers)
Literal integers are represented in the standard manner:
```julia-repl
julia> 1
1

julia> 1234
1234
```
The default type for an integer literal depends on whether the target system has a 32-bit architecture or a 64-bit architecture:
```julia-repl
# 32-bit system:
julia> typeof(1)
Int32

# 64-bit system:
julia> typeof(1)
Int64
```
The Julia internal variable [`Sys.WORD_SIZE`](../../base/constants/#Base.Sys.WORD_SIZE) indicates whether the target system is 32-bit or 64-bit:
```julia-repl
# 32-bit system:
julia> Sys.WORD_SIZE
32

# 64-bit system:
julia> Sys.WORD_SIZE
64
```
Julia also defines the types `Int` and `UInt`, which are aliases for the system's signed and unsigned native integer types respectively:
```julia-repl
# 32-bit system:
julia> Int
Int32
julia> UInt
UInt32

# 64-bit system:
julia> Int
Int64
julia> UInt
UInt64
```
Larger integer literals that cannot be represented using only 32 bits but can be represented in 64 bits always create 64-bit integers, regardless of the system type:
```julia-repl
# 32-bit or 64-bit system:
julia> typeof(3000000000)
Int64
```
Unsigned integers are input and output using the `0x` prefix and hexadecimal (base 16) digits `0-9a-f` (the capitalized digits `A-F` also work for input). The size of the unsigned value is determined by the number of hex digits used:


## [Integers](#Integers)
```julia-repl
julia> x = 0x1
0x01

julia> typeof(x)
UInt8

julia> x = 0x123
0x0123

julia> typeof(x)
UInt16

julia> x = 0x1234567
0x01234567

julia> typeof(x)
UInt32

julia> x = 0x123456789abcdef
0x0123456789abcdef

julia> typeof(x)
UInt64

julia> x = 0x11112222333344445555666677778888
0x11112222333344445555666677778888

julia> typeof(x)
UInt128
```
This behavior is based on the observation that when one uses unsigned hex literals for integer values, one typically is using them to represent a fixed numeric byte sequence, rather than just an integer value.
Binary and octal literals are also supported:
```julia-repl
julia> x = 0b10
0x02

julia> typeof(x)
UInt8

julia> x = 0o010
0x08

julia> typeof(x)
UInt8

julia> x = 0x00000000000000001111222233334444
0x00000000000000001111222233334444

julia> typeof(x)
UInt128
```
As for hexadecimal literals, binary and octal literals produce unsigned integer types. The size of the binary data item is the minimal needed size, if the leading digit of the literal is not `0`. In the case of leading zeros, the size is determined by the minimal needed size for a literal, which has the same length but leading digit `1`. It means that:
-   `0x1` and `0x12` are `UInt8` literals,
-   `0x123` and `0x1234` are `UInt16` literals,
-   `0x12345` and `0x12345678` are `UInt32` literals,
-   `0x123456789` and `0x1234567890adcdef` are `UInt64` literals, etc.


## [Integers](#Integers)
Even if there are leading zero digits which don’t contribute to the value, they count for determining storage size of a literal. So `0x01` is a `UInt8` while `0x0001` is a `UInt16`.
That allows the user to control the size.
Unsigned literals (starting with `0x`) that encode integers too large to be represented as `UInt128` values will construct `BigInt` values instead. This is not an unsigned type but it is the only built-in type big enough to represent such large integer values.
Binary, octal, and hexadecimal literals may be signed by a `-` immediately preceding the unsigned literal. They produce an unsigned integer of the same size as the unsigned literal would do, with the two's complement of the value:
```julia-repl
julia> -0x2
0xfe

julia> -0x0002
0xfffe
```
The minimum and maximum representable values of primitive numeric types such as integers are given by the [`typemin`](../../base/base/#Base.typemin) and [`typemax`](../../base/base/#Base.typemax) functions:


## [Integers](#Integers)
```julia-repl
julia> (typemin(Int32), typemax(Int32))
(-2147483648, 2147483647)

julia> for T in [Int8,Int16,Int32,Int64,Int128,UInt8,UInt16,UInt32,UInt64,UInt128]
           println("$(lpad(T,7)): [$(typemin(T)),$(typemax(T))]")
       end
   Int8: [-128,127]
  Int16: [-32768,32767]
  Int32: [-2147483648,2147483647]
  Int64: [-9223372036854775808,9223372036854775807]
 Int128: [-170141183460469231731687303715884105728,170141183460469231731687303715884105727]
  UInt8: [0,255]
 UInt16: [0,65535]
 UInt32: [0,4294967295]
 UInt64: [0,18446744073709551615]
UInt128: [0,340282366920938463463374607431768211455]
```
The values returned by [`typemin`](../../base/base/#Base.typemin) and [`typemax`](../../base/base/#Base.typemax) are always of the given argument type. (The above expression uses several features that have yet to be introduced, including [for loops](../control-flow/#man-loops), [Strings](../strings/#man-strings), and [Interpolation](../strings/#string-interpolation), but should be easy enough to understand for users with some existing programming experience.)


### [Overflow behavior](#Overflow-behavior)
In Julia, exceeding the maximum representable value of a given type results in a wraparound behavior:
```julia-repl
julia> x = typemax(Int64)
9223372036854775807

julia> x + 1
-9223372036854775808

julia> x + 1 == typemin(Int64)
true
```
Arithmetic operations with Julia's integer types inherently perform [modular arithmetic](https://en.wikipedia.org/wiki/Modular_arithmetic), mirroring the characteristics of integer arithmetic on modern computer hardware. In scenarios where overflow is a possibility, it is crucial to explicitly check for wraparound effects that can result from such overflows. The [`Base.Checked`](../../base/math/#Base.Checked) module provides a suite of arithmetic operations equipped with overflow checks, which trigger errors if an overflow occurs. For use cases where overflow cannot be tolerated under any circumstances, utilizing the [`BigInt`](../../base/numbers/#Base.GMP.BigInt) type, as detailed in [Arbitrary Precision Arithmetic](#Arbitrary-Precision-Arithmetic), is advisable.
An example of overflow behavior and how to potentially resolve it is as follows:
```julia-repl
julia> 10^19
-8446744073709551616

julia> big(10)^19
10000000000000000000
```


### [Division errors](#Division-errors)
Integer division (the `div` function) has two exceptional cases: dividing by zero, and dividing the lowest negative number ([`typemin`](../../base/base/#Base.typemin)) by -1. Both of these cases throw a [`DivideError`](../../base/base/#Core.DivideError). The remainder and modulus functions (`rem` and `mod`) throw a [`DivideError`](../../base/base/#Core.DivideError) when their second argument is zero.


## [Floating-Point Numbers](#Floating-Point-Numbers)
Literal floating-point numbers are represented in the standard formats, using [E-notation](https://en.wikipedia.org/wiki/Scientific_notation#E_notation) when necessary:
```julia-repl
julia> 1.0
1.0

julia> 1.
1.0

julia> 0.5
0.5

julia> .5
0.5

julia> -1.23
-1.23

julia> 1e10
1.0e10

julia> 2.5e-4
0.00025
```
The above results are all [`Float64`](../../base/numbers/#Core.Float64) values. Literal [`Float32`](../../base/numbers/#Core.Float32) values can be entered by writing an `f` in place of `e`:
```julia-repl
julia> x = 0.5f0
0.5f0

julia> typeof(x)
Float32

julia> 2.5f-4
0.00025f0
```
Values can be converted to [`Float32`](../../base/numbers/#Core.Float32) easily:
```julia-repl
julia> x = Float32(-1.5)
-1.5f0

julia> typeof(x)
Float32
```
Hexadecimal floating-point literals are also valid, but only as [`Float64`](../../base/numbers/#Core.Float64) values, with `p` preceding the base-2 exponent:
```julia-repl
julia> 0x1p0
1.0

julia> 0x1.8p3
12.0

julia> x = 0x.4p-1
0.125

julia> typeof(x)
Float64
```


## [Floating-Point Numbers](#Floating-Point-Numbers)
Half-precision floating-point numbers are also supported ([`Float16`](../../base/numbers/#Core.Float16)) on all platforms, with native instructions used on hardware which supports this number format. Otherwise, operations are implemented in software, and use [`Float32`](../../base/numbers/#Core.Float32) for intermediate calculations. As an internal implementation detail, this is achieved under the hood by using LLVM's [`half`](https://llvm.org/docs/LangRef.html#half-precision-floating-point-intrinsics) type, which behaves similarly to what the GCC [`-fexcess-precision=16`](https://gcc.gnu.org/onlinedocs/gcc/Optimize-Options.html#index-fexcess-precision) flag does for C/C++ code.
```julia-repl
julia> sizeof(Float16(4.))
2

julia> 2*Float16(4.)
Float16(8.0)
```
The underscore `_` can be used as digit separator:
```julia-repl
julia> 10_000, 0.000_000_005, 0xdead_beef, 0b1011_0010
(10000, 5.0e-9, 0xdeadbeef, 0xb2)
```


### [Floating-point zero](#Floating-point-zero)
Floating-point numbers have [two zeros](https://en.wikipedia.org/wiki/Signed_zero), positive zero and negative zero. They are equal to each other but have different binary representations, as can be seen using the [`bitstring`](../../base/numbers/#Base.bitstring) function:
```julia-repl
julia> 0.0 == -0.0
true

julia> bitstring(0.0)
"0000000000000000000000000000000000000000000000000000000000000000"

julia> bitstring(-0.0)
"1000000000000000000000000000000000000000000000000000000000000000"
```


### [Special floating-point values](#Special-floating-point-values)
There are three specified standard floating-point values that do not correspond to any point on the real number line:
| `Float16` | `Float32` | `Float64` | Name              | Description                                                     |
|:----------|:----------|:----------|:------------------|:----------------------------------------------------------------|
| `Inf16`   | `Inf32`   | `Inf`     | positive infinity | a value greater than all finite floating-point values           |
| `-Inf16`  | `-Inf32`  | `-Inf`    | negative infinity | a value less than all finite floating-point values              |
| `NaN16`   | `NaN32`   | `NaN`     | not a number      | a value not `==` to any floating-point value (including itself) |
For further discussion of how these non-finite floating-point values are ordered with respect to each other and other floats, see [Numeric Comparisons](../mathematical-operations/#Numeric-Comparisons). By the [IEEE 754 standard](https://en.wikipedia.org/wiki/IEEE_754-2008), these floating-point values are the results of certain arithmetic operations:
```julia-repl
julia> 1/Inf
0.0

julia> 1/0
Inf

julia> -5/0
-Inf

julia> 0.000001/0
Inf

julia> 0/0
NaN

julia> 500 + Inf
Inf

julia> 500 - Inf
-Inf

julia> Inf + Inf
Inf

julia> Inf - Inf
NaN

julia> Inf * Inf
Inf

julia> Inf / Inf
NaN

julia> 0 * Inf
NaN

julia> NaN == NaN
false

julia> NaN != NaN
true

julia> NaN < NaN
false

julia> NaN > NaN
false
```


### [Special floating-point values](#Special-floating-point-values)
The [`typemin`](../../base/base/#Base.typemin) and [`typemax`](../../base/base/#Base.typemax) functions also apply to floating-point types:
```julia-repl
julia> (typemin(Float16),typemax(Float16))
(-Inf16, Inf16)

julia> (typemin(Float32),typemax(Float32))
(-Inf32, Inf32)

julia> (typemin(Float64),typemax(Float64))
(-Inf, Inf)
```


### [Machine epsilon](#Machine-epsilon)
Most real numbers cannot be represented exactly with floating-point numbers, and so for many purposes it is important to know the distance between two adjacent representable floating-point numbers, which is often known as [machine epsilon](https://en.wikipedia.org/wiki/Machine_epsilon).
Julia provides [`eps`](../../base/base/#Base.eps-Tuple%7BType%7B%3C:AbstractFloat%7D%7D), which gives the distance between `1.0` and the next larger representable floating-point value:
```julia-repl
julia> eps(Float32)
1.1920929f-7

julia> eps(Float64)
2.220446049250313e-16

julia> eps() # same as eps(Float64)
2.220446049250313e-16
```
These values are `2.0^-23` and `2.0^-52` as [`Float32`](../../base/numbers/#Core.Float32) and [`Float64`](../../base/numbers/#Core.Float64) values, respectively. The [`eps`](../../base/base/#Base.eps-Tuple%7BType%7B%3C:AbstractFloat%7D%7D) function can also take a floating-point value as an argument, and gives the absolute difference between that value and the next representable floating point value. That is, `eps(x)` yields a value of the same type as `x` such that `x + eps(x)` is the next representable floating-point value larger than `x`:
```julia-repl
julia> eps(1.0)
2.220446049250313e-16

julia> eps(1000.)
1.1368683772161603e-13

julia> eps(1e-27)
1.793662034335766e-43

julia> eps(0.0)
5.0e-324
```


### [Machine epsilon](#Machine-epsilon)
The distance between two adjacent representable floating-point numbers is not constant, but is smaller for smaller values and larger for larger values. In other words, the representable floating-point numbers are densest in the real number line near zero, and grow sparser exponentially as one moves farther away from zero. By definition, `eps(1.0)` is the same as `eps(Float64)` since `1.0` is a 64-bit floating-point value.
Julia also provides the [`nextfloat`](../../base/numbers/#Base.nextfloat) and [`prevfloat`](../../base/numbers/#Base.prevfloat) functions which return the next largest or smallest representable floating-point number to the argument respectively:
```julia-repl
julia> x = 1.25f0
1.25f0

julia> nextfloat(x)
1.2500001f0

julia> prevfloat(x)
1.2499999f0

julia> bitstring(prevfloat(x))
"00111111100111111111111111111111"

julia> bitstring(x)
"00111111101000000000000000000000"

julia> bitstring(nextfloat(x))
"00111111101000000000000000000001"
```
This example highlights the general principle that the adjacent representable floating-point numbers also have adjacent binary integer representations.


### [Rounding modes](#Rounding-modes)
If a number doesn't have an exact floating-point representation, it must be rounded to an appropriate representable value. However, the manner in which this rounding is done can be changed if required according to the rounding modes presented in the [IEEE 754 standard](https://en.wikipedia.org/wiki/IEEE_754-2008).
The default mode used is always [`RoundNearest`](../../base/math/#Base.Rounding.RoundNearest), which rounds to the nearest representable value, with ties rounded towards the nearest value with an even least significant bit.


### [Background and References](#Background-and-References)
Floating-point arithmetic entails many subtleties which can be surprising to users who are unfamiliar with the low-level implementation details. However, these subtleties are described in detail in most books on scientific computation, and also in the following references:
-   The definitive guide to floating point arithmetic is the [IEEE 754-2008 Standard](https://standards.ieee.org/standard/754-2008.html); however, it is not available for free online.
-   For a brief but lucid presentation of how floating-point numbers are represented, see John D. Cook's [article](https://www.johndcook.com/blog/2009/04/06/anatomy-of-a-floating-point-number/) on the subject as well as his [introduction](https://www.johndcook.com/blog/2009/04/06/numbers-are-a-leaky-abstraction/) to some of the issues arising from how this representation differs in behavior from the idealized abstraction of real numbers.
-   Also recommended is Bruce Dawson's [series of blog posts on floating-point numbers](https://randomascii.wordpress.com/2012/05/20/thats-not-normalthe-performance-of-odd-floats/).
-   For an excellent, in-depth discussion of floating-point numbers and issues of numerical accuracy encountered when computing with them, see David Goldberg's paper [What Every Computer Scientist Should Know About Floating-Point Arithmetic](https://citeseerx.ist.psu.edu/viewdoc/download?doi=10.1.1.22.6768&rep=rep1&type=pdf).


### [Background and References](#Background-and-References)
-   For even more extensive documentation of the history of, rationale for, and issues with floating-point numbers, as well as discussion of many other topics in numerical computing, see the [collected writings](https://people.eecs.berkeley.edu/~wkahan/) of [William Kahan](https://en.wikipedia.org/wiki/William_Kahan), commonly known as the "Father of Floating-Point". Of particular interest may be [An Interview with the Old Man of Floating-Point](https://people.eecs.berkeley.edu/~wkahan/ieee754status/754story.html).


## [Arbitrary Precision Arithmetic](#Arbitrary-Precision-Arithmetic)
To allow computations with arbitrary-precision integers and floating point numbers, Julia wraps the [GNU Multiple Precision Arithmetic Library (GMP)](https://gmplib.org) and the [GNU MPFR Library](https://www.mpfr.org), respectively. The [`BigInt`](../../base/numbers/#Base.GMP.BigInt) and [`BigFloat`](../../base/numbers/#Base.MPFR.BigFloat) types are available in Julia for arbitrary precision integer and floating point numbers respectively.
Constructors exist to create these types from primitive numerical types, and the [string literal](../strings/#non-standard-string-literals) [`@big_str`](../../base/numbers/#Core.@big_str) or [`parse`](../../base/numbers/#Base.parse) can be used to construct them from `AbstractString`s. `BigInt`s can also be input as integer literals when they are too big for other built-in integer types. Note that as there is no unsigned arbitrary-precision integer type in `Base` (`BigInt` is sufficient in most cases), hexadecimal, octal and binary literals can be used (in addition to decimal literals).
Once created, they participate in arithmetic with all other numeric types thanks to Julia's [type promotion and conversion mechanism](../conversion-and-promotion/#conversion-and-promotion):


## [Arbitrary Precision Arithmetic](#Arbitrary-Precision-Arithmetic)
```julia-repl
julia> BigInt(typemax(Int64)) + 1
9223372036854775808

julia> big"123456789012345678901234567890" + 1
123456789012345678901234567891

julia> parse(BigInt, "123456789012345678901234567890") + 1
123456789012345678901234567891

julia> string(big"2"^200, base=16)
"100000000000000000000000000000000000000000000000000"

julia> 0x100000000000000000000000000000000-1 == typemax(UInt128)
true

julia> 0x000000000000000000000000000000000
0

julia> typeof(ans)
BigInt

julia> big"1.23456789012345678901"
1.234567890123456789010000000000000000000000000000000000000000000000000000000004

julia> parse(BigFloat, "1.23456789012345678901")
1.234567890123456789010000000000000000000000000000000000000000000000000000000004

julia> BigFloat(2.0^66) / 3
2.459565876494606882133333333333333333333333333333333333333333333333333333333344e+19

julia> factorial(BigInt(40))
815915283247897734345611269596115894272000000000
```
However, type promotion between the primitive types above and [`BigInt`](../../base/numbers/#Base.GMP.BigInt)/[`BigFloat`](../../base/numbers/#Base.MPFR.BigFloat) is not automatic and must be explicitly stated.
```julia-repl
julia> x = typemin(Int64)
-9223372036854775808

julia> x = x - 1
9223372036854775807

julia> typeof(x)
Int64

julia> y = BigInt(typemin(Int64))
-9223372036854775808

julia> y = y - 1
-9223372036854775809

julia> typeof(y)
BigInt
```


## [Arbitrary Precision Arithmetic](#Arbitrary-Precision-Arithmetic)
The default precision (in number of bits of the significand) and rounding mode of [`BigFloat`](../../base/numbers/#Base.MPFR.BigFloat) operations can be changed globally by calling [`setprecision`](../../base/numbers/#Base.MPFR.setprecision) and [`setrounding`](../../base/numbers/#Base.Rounding.setrounding-Tuple%7BType,%20Any%7D), and all further calculations will take these changes in account. Alternatively, the precision or the rounding can be changed only within the execution of a particular block of code by using the same functions with a `do` block:
```julia-repl
julia> setrounding(BigFloat, RoundUp) do
           BigFloat(1) + parse(BigFloat, "0.1")
       end
1.100000000000000000000000000000000000000000000000000000000000000000000000000003

julia> setrounding(BigFloat, RoundDown) do
           BigFloat(1) + parse(BigFloat, "0.1")
       end
1.099999999999999999999999999999999999999999999999999999999999999999999999999986

julia> setprecision(40) do
           BigFloat(1) + parse(BigFloat, "0.1")
       end
1.1000000000004
```
The relation between [`setprecision`](../../base/numbers/#Base.MPFR.setprecision) or [`setrounding`](../../base/numbers/#Base.Rounding.setrounding-Tuple%7BType,%20Any%7D) and [`@big_str`](../../base/numbers/#Core.@big_str), the macro used for `big` string literals (such as `big"0.3"`), might not be intuitive, as a consequence of the fact that `@big_str` is a macro. See the [`@big_str`](../../base/numbers/#Core.@big_str) documentation for details.


## [Numeric Literal Coefficients](#man-numeric-literal-coefficients)
To make common numeric formulae and expressions clearer, Julia allows variables to be immediately preceded by a numeric literal, implying multiplication. This makes writing polynomial expressions much cleaner:
```julia-repl
julia> x = 3
3

julia> 2x^2 - 3x + 1
10

julia> 1.5x^2 - .5x + 1
13.0
```
It also makes writing exponential functions more elegant:
```julia-repl
julia> 2^2x
64
```
The precedence of numeric literal coefficients is slightly lower than that of unary operators such as negation. So `-2x` is parsed as `(-2) * x` and `√2x` is parsed as `(√2) * x`. However, numeric literal coefficients parse similarly to unary operators when combined with exponentiation. For example `2^3x` is parsed as `2^(3x)`, and `2x^3` is parsed as `2*(x^3)`.
Numeric literals also work as coefficients to parenthesized expressions:
```julia-repl
julia> 2(x-1)^2 - 3(x-1) + 1
3
```
The precedence of numeric literal coefficients used for implicit multiplication is higher than other binary operators such as multiplication (`*`), and division (`/`, `\`, and `//`). This means, for example, that `1 / 2im` equals `-0.5im` and `6 // 2(2 + 1)` equals `1 // 1`.
Additionally, parenthesized expressions can be used as coefficients to variables, implying multiplication of the expression by the variable:
```julia-repl
julia> (x-1)x
6
```
Neither juxtaposition of two parenthesized expressions, nor placing a variable before a parenthesized expression, however, can be used to imply multiplication:


## [Numeric Literal Coefficients](#man-numeric-literal-coefficients)
```julia-repl
julia> (x-1)(x+1)
ERROR: MethodError: objects of type Int64 are not callable

julia> x(x+1)
ERROR: MethodError: objects of type Int64 are not callable
```
Both expressions are interpreted as function application: any expression that is not a numeric literal, when immediately followed by a parenthetical, is interpreted as a function applied to the values in parentheses (see [Functions](../faq/#Functions) for more about functions). Thus, in both of these cases, an error occurs since the left-hand value is not a function.
The above syntactic enhancements significantly reduce the visual noise incurred when writing common mathematical formulae. Note that no whitespace may come between a numeric literal coefficient and the identifier or parenthesized expression which it multiplies.


### [Syntax Conflicts](#Syntax-Conflicts)
Juxtaposed literal coefficient syntax may conflict with some numeric literal syntaxes: hexadecimal, octal and binary integer literals and engineering notation for floating-point literals. Here are some situations where syntactic conflicts arise:
-   The hexadecimal integer literal expression `0xff` could be interpreted as the numeric literal `0` multiplied by the variable `xff`. Similar ambiguities arise with octal and binary literals like `0o777` or `0b01001010`.
-   The floating-point literal expression `1e10` could be interpreted as the numeric literal `1` multiplied by the variable `e10`, and similarly with the equivalent `E` form.
-   The 32-bit floating-point literal expression `1.5f22` could be interpreted as the numeric literal `1.5` multiplied by the variable `f22`.
In all cases the ambiguity is resolved in favor of interpretation as numeric literals:
-   Expressions starting with `0x`/`0o`/`0b` are always hexadecimal/octal/binary literals.
-   Expressions starting with a numeric literal followed by `e` or `E` are always floating-point literals.
-   Expressions starting with a numeric literal followed by `f` are always 32-bit floating-point literals.
Unlike `E`, which is equivalent to `e` in numeric literals for historical reasons, `F` is just another letter and does not behave like `f` in numeric literals. Hence, expressions starting with a numeric literal followed by `F` are interpreted as the numerical literal multiplied by a variable, which means that, for example, `1.5F22` is equal to `1.5 * F22`.


## [Literal zero and one](#Literal-zero-and-one)
Julia provides functions which return literal 0 and 1 corresponding to a specified type or the type of a given variable.
| Function                                   | Description                                      |
|:-------------------------------------------|:-------------------------------------------------|
| [`zero(x)`](../../base/numbers/#Base.zero) | Literal zero of type `x` or type of variable `x` |
| [`one(x)`](../../base/numbers/#Base.one)   | Literal one of type `x` or type of variable `x`  |
These functions are useful in [Numeric Comparisons](../mathematical-operations/#Numeric-Comparisons) to avoid overhead from unnecessary [type conversion](../conversion-and-promotion/#conversion-and-promotion).
Examples:
```julia-repl
julia> zero(Float32)
0.0f0

julia> zero(1.0)
0.0

julia> one(Int32)
1

julia> one(BigFloat)
1.0
```
------------------------------------------------------------------------


# Mathematical Operations and Elementary Functions · The Julia Language
Source: https://docs.julialang.org/en/v1/manual/mathematical-operations/


# [Mathematical Operations and Elementary Functions](#Mathematical-Operations-and-Elementary-Functions)
Julia provides a complete collection of basic arithmetic and bitwise operators across all of its numeric primitive types, as well as providing portable, efficient implementations of a comprehensive collection of standard mathematical functions.


## [Arithmetic Operators](#Arithmetic-Operators)
The following [arithmetic operators](https://en.wikipedia.org/wiki/Arithmetic#Arithmetic_operations) are supported on all primitive numeric types:
| Expression | Name           | Description                            |
|:-----------|:---------------|:---------------------------------------|
| `+x`       | unary plus     | the identity operation                 |
| `-x`       | unary minus    | maps values to their additive inverses |
| `x + y`    | binary plus    | performs addition                      |
| `x - y`    | binary minus   | performs subtraction                   |
| `x * y`    | times          | performs multiplication                |
| `x / y`    | divide         | performs division                      |
| `x ÷ y`    | integer divide | x / y, truncated to an integer         |
| `x \ y`    | inverse divide | equivalent to `y / x`                  |
| `x ^ y`    | power          | raises `x` to the `y`th power          |
| `x % y`    | remainder      | equivalent to `rem(x, y)`              |
A numeric literal placed directly before an identifier or parentheses, e.g. `2x` or `2(x + y)`, is treated as a multiplication, except with higher precedence than other binary operations. See [Numeric Literal Coefficients](../integers-and-floating-point-numbers/#man-numeric-literal-coefficients) for details.


## [Arithmetic Operators](#Arithmetic-Operators)
Julia's promotion system makes arithmetic operations on mixtures of argument types "just work" naturally and automatically. See [Conversion and Promotion](../conversion-and-promotion/#conversion-and-promotion) for details of the promotion system.
The ÷ sign can be conveniently typed by writing `\div<tab>` to the REPL or Julia IDE. See the [manual section on Unicode input](../unicode-input/#Unicode-Input) for more information.
Here are some simple examples using arithmetic operators:
```julia-repl
julia> 1 + 2 + 3
6

julia> 1 - 2
-1

julia> 3*2/12
0.5
```
(By convention, we tend to space operators more tightly if they get applied before other nearby operators. For instance, we would generally write `-x + 2` to reflect that first `x` gets negated, and then `2` is added to that result.)
When used in multiplication, `false` acts as a *strong zero*:
```julia-repl
julia> NaN * false
0.0

julia> false * Inf
0.0
```
This is useful for preventing the propagation of `NaN` values in quantities that are known to be zero. See [Knuth (1992)](https://arxiv.org/abs/math/9205211) for motivation.


## [Boolean Operators](#Boolean-Operators)
The following [Boolean operators](https://en.wikipedia.org/wiki/Boolean_algebra#Operations) are supported on [`Bool`](../../base/numbers/#Core.Bool) types:
| Expression | Name                                                                |
|:-----------|:--------------------------------------------------------------------|
| `!x`       | negation                                                            |
| `x && y`   | [short-circuiting and](../control-flow/#man-conditional-evaluation) |
| `x || y`   | [short-circuiting or](../control-flow/#man-conditional-evaluation)  |
Negation changes `true` to `false` and vice versa. The short-circuiting operations are explained on the linked page.
Note that `Bool` is an integer type and all the usual promotion rules and numeric operators are also defined on it.


## [Bitwise Operators](#Bitwise-Operators)
The following [bitwise operators](https://en.wikipedia.org/wiki/Bitwise_operation#Bitwise_operators) are supported on all primitive integer types:
| Expression | Name                                                                     |
|:-----------|:-------------------------------------------------------------------------|
| `~x`       | bitwise not                                                              |
| `x & y`    | bitwise and                                                              |
| `x | y`    | bitwise or                                                               |
| `x ⊻ y`    | bitwise xor (exclusive or)                                               |
| `x ⊼ y`    | bitwise nand (not and)                                                   |
| `x ⊽ y`    | bitwise nor (not or)                                                     |
| `x >>> y`  | [logical shift](https://en.wikipedia.org/wiki/Logical_shift) right       |
| `x >> y`   | [arithmetic shift](https://en.wikipedia.org/wiki/Arithmetic_shift) right |
| `x << y`   | logical/arithmetic shift left                                            |
Here are some examples with bitwise operators:
```julia-repl
julia> ~123
-124

julia> 123 & 234
106

julia> 123 | 234
251

julia> 123 ⊻ 234
145

julia> xor(123, 234)
145

julia> nand(123, 123)
-124

julia> 123 ⊼ 123
-124

julia> nor(123, 124)
-128

julia> 123 ⊽ 124
-128

julia> ~UInt32(123)
0xffffff84

julia> ~UInt8(123)
0x84
```


## [Updating operators](#Updating-operators)
Every binary arithmetic and bitwise operator also has an updating version that assigns the result of the operation back into its left operand. The updating version of the binary operator is formed by placing a `=` immediately after the operator. For example, writing `x += 3` is equivalent to writing `x = x + 3`:
```julia-repl
julia> x = 1
1

julia> x += 3
4

julia> x
4
```
The updating versions of all the binary arithmetic and bitwise operators are:
```julia
+=  -=  *=  /=  \=  ÷=  %=  ^=  &=  |=  ⊻=  >>>=  >>=  <<=
```
An updating operator rebinds the variable on the left-hand side. As a result, the type of the variable may change.
```julia-repl
julia> x = 0x01; typeof(x)
UInt8

julia> x *= 2 # Same as x = x * 2
2

julia> typeof(x)
Int64
```


## [Vectorized "dot" operators](#man-dot-operators)
For *every* binary operation like `^`, there is a corresponding "dot" operation `.^` that is *automatically* defined to perform `^` element-by-element on arrays. For example, `[1, 2, 3] ^ 3` is not defined, since there is no standard mathematical meaning to "cubing" a (non-square) array, but `[1, 2, 3] .^ 3` is defined as computing the elementwise (or "vectorized") result `[1^3, 2^3, 3^3]`. Similarly for unary operators like `!` or `√`, there is a corresponding `.√` that applies the operator elementwise.
```julia-repl
julia> [1, 2, 3] .^ 3
3-element Vector{Int64}:
  1
  8
 27
```
More specifically, `a .^ b` is parsed as the ["dot" call](../functions/#man-vectorized) `(^).(a,b)`, which performs a [broadcast](../arrays/#Broadcasting) operation: it can combine arrays and scalars, arrays of the same size (performing the operation elementwise), and even arrays of different shapes (e.g. combining row and column vectors to produce a matrix). Moreover, like all vectorized "dot calls," these "dot operators" are *fusing*. For example, if you compute `2 .* A.^2 .+ sin.(A)` (or equivalently `@. 2A^2 + sin(A)`, using the [`@.`](../../base/arrays/#Base.Broadcast.@__dot__) macro) for an array `A`, it performs a *single* loop over `A`, computing `2a^2 + sin(a)` for each element `a` of `A`. In particular, nested dot calls like `f.(g.(x))` are fused, and "adjacent" binary operators like `x .+ 3 .* x.^2` are equivalent to nested dot calls `(+).(x, (*).(3, (^).(x, 2)))`.


## [Vectorized "dot" operators](#man-dot-operators)
Furthermore, "dotted" updating operators like `a .+= b` (or `@. a += b`) are parsed as `a .= a .+ b`, where `.=` is a fused *in-place* assignment operation (see the [dot syntax documentation](../functions/#man-vectorized)).
Note the dot syntax is also applicable to user-defined operators. For example, if you define `⊗(A, B) = kron(A, B)` to give a convenient infix syntax `A ⊗ B` for Kronecker products ([`kron`](../../stdlib/LinearAlgebra/#Base.kron)), then `[A, B] .⊗ [C, D]` will compute `[A⊗C, B⊗D]` with no additional coding.
Combining dot operators with numeric literals can be ambiguous. For example, it is not clear whether `1.+x` means `1. + x` or `1 .+ x`. Therefore this syntax is disallowed, and spaces must be used around the operator in such cases.


## [Numeric Comparisons](#Numeric-Comparisons)
Standard comparison operations are defined for all the primitive numeric types:
| Operator                                                                | Name                     |
|:------------------------------------------------------------------------|:-------------------------|
| [`==`](../../base/math/#Base.:==)                                       | equality                 |
| [`!=`](../../base/math/#Base.:!=), [`≠`](../../base/math/#Base.:!=)     | inequality               |
| [`<`](../../base/math/#Base.:%3C)                                       | less than                |
| [`<=`](../../base/math/#Base.:%3C=), [`≤`](../../base/math/#Base.:%3C=) | less than or equal to    |
| [`>`](../../base/math/#Base.:%3E)                                       | greater than             |
| [`>=`](../../base/math/#Base.:%3E=), [`≥`](../../base/math/#Base.:%3E=) | greater than or equal to |
Here are some simple examples:
```julia-repl
julia> 1 == 1
true

julia> 1 == 2
false

julia> 1 != 2
true

julia> 1 == 1.0
true

julia> 1 < 2
true

julia> 1.0 > 3
false

julia> 1 >= 1.0
true

julia> -1 <= 1
true

julia> -1 <= -1
true

julia> -1 <= -2
false

julia> 3 < -0.5
false
```
Integers are compared in the standard manner – by comparison of bits. Floating-point numbers are compared according to the [IEEE 754 standard](https://en.wikipedia.org/wiki/IEEE_754-2008):
-   Finite numbers are ordered in the usual manner.
-   Positive zero is equal but not greater than negative zero.


## [Numeric Comparisons](#Numeric-Comparisons)
-   `Inf` is equal to itself and greater than everything else except `NaN`.
-   `-Inf` is equal to itself and less than everything else except `NaN`.
-   `NaN` is not equal to, not less than, and not greater than anything, including itself.
The last point is potentially surprising and thus worth noting:
```julia-repl
julia> NaN == NaN
false

julia> NaN != NaN
true

julia> NaN < NaN
false

julia> NaN > NaN
false
```
and can cause headaches when working with [arrays](../arrays/#man-multi-dim-arrays):
```julia-repl
julia> [1 NaN] == [1 NaN]
false
```
Julia provides additional functions to test numbers for special values, which can be useful in situations like hash key comparisons:
| Function                                           | Tests if                  |
|:---------------------------------------------------|:--------------------------|
| [`isequal(x, y)`](../../base/base/#Base.isequal)   | `x` and `y` are identical |
| [`isfinite(x)`](../../base/numbers/#Base.isfinite) | `x` is a finite number    |
| [`isinf(x)`](../../base/numbers/#Base.isinf)       | `x` is infinite           |
| [`isnan(x)`](../../base/numbers/#Base.isnan)       | `x` is not a number       |
[`isequal`](../../base/base/#Base.isequal) considers `NaN`s equal to each other:
```julia-repl
julia> isequal(NaN, NaN)
true

julia> isequal([1 NaN], [1 NaN])
true

julia> isequal(NaN, NaN32)
true
```
`isequal` can also be used to distinguish signed zeros:
```julia-repl
julia> -0.0 == 0.0
true

julia> isequal(-0.0, 0.0)
false
```


## [Numeric Comparisons](#Numeric-Comparisons)
Mixed-type comparisons between signed integers, unsigned integers, and floats can be tricky. A great deal of care has been taken to ensure that Julia does them correctly.
For other types, `isequal` defaults to calling [`==`](../../base/math/#Base.:==), so if you want to define equality for your own types then you only need to add a [`==`](../../base/math/#Base.:==) method. If you define your own equality function, you should probably define a corresponding [`hash`](../../base/base/#Base.hash) method to ensure that `isequal(x,y)` implies `hash(x) == hash(y)`.


### [Chaining comparisons](#Chaining-comparisons)
Unlike most languages, with the [notable exception of Python](https://en.wikipedia.org/wiki/Python_syntax_and_semantics#Comparison_operators), comparisons can be arbitrarily chained:
```julia-repl
julia> 1 < 2 <= 2 < 3 == 3 > 2 >= 1 == 1 < 3 != 5
true
```
Chaining comparisons is often quite convenient in numerical code. Chained comparisons use the `&&` operator for scalar comparisons, and the [`&`](../../base/math/#Base.:&) operator for elementwise comparisons, which allows them to work on arrays. For example, `0 .< A .< 1` gives a boolean array whose entries are true where the corresponding elements of `A` are between 0 and 1.
Note the evaluation behavior of chained comparisons:
```julia-repl
julia> v(x) = (println(x); x)
v (generic function with 1 method)

julia> v(1) < v(2) <= v(3)
2
1
3
true

julia> v(1) > v(2) <= v(3)
2
1
false
```
The middle expression is only evaluated once, rather than twice as it would be if the expression were written as `v(1) < v(2) && v(2) <= v(3)`. However, the order of evaluations in a chained comparison is undefined. It is strongly recommended not to use expressions with side effects (such as printing) in chained comparisons. If side effects are required, the short-circuit `&&` operator should be used explicitly (see [Short-Circuit Evaluation](../control-flow/#Short-Circuit-Evaluation)).


### [Elementary Functions](#Elementary-Functions)
Julia provides a comprehensive collection of mathematical functions and operators. These mathematical operations are defined over as broad a class of numerical values as permit sensible definitions, including integers, floating-point numbers, rationals, and complex numbers, wherever such definitions make sense.
Moreover, these functions (like any Julia function) can be applied in "vectorized" fashion to arrays and other collections with the [dot syntax](../functions/#man-vectorized) `f.(A)`, e.g. `sin.(A)` will compute the sine of each element of an array `A`.


## [Operator Precedence and Associativity](#Operator-Precedence-and-Associativity)
Julia applies the following order and associativity of operations, from highest precedence to lowest:
| Category       | Operators                                             | Associativity                                                |
|:---------------|:------------------------------------------------------|:-------------------------------------------------------------|
| Syntax         | `.` followed by `::`                                  | Left                                                         |
| Exponentiation | `^`                                                   | Right                                                        |
| Unary          | `+ - ! ~ ¬ √ ∛ ∜ ⋆ ± ∓ <: >:`                         | Right[[1\]](#footnote-1) |
| Bitshifts      | `<< >> >>>`                                           | Left                                                         |
| Fractions      | `//`                                                  | Left                                                         |
| Multiplication | `* / % & \ ÷`                                         | Left[[2\]](#footnote-2)  |
| Addition       | `+ - | ⊻`                                             | Left[[2\]](#footnote-2)  |
| Syntax         | `: ..`                                                | Left                                                         |
| Syntax         | `|>`                                                  | Left                                                         |
| Syntax         | `<|`                                                  | Right                                                        |
| Comparisons    | `> < >= <= == === != !== <:`                          | Non-associative                                              |
| Control flow   | `&&` followed by `||` followed by `?`                 | Right                                                        |
| Pair           | `=>`                                                  | Right                                                        |
| Assignments    | `= += -= *= /= //= \= ^= ÷= %= |= &= ⊻= <<= >>= >>>=` | Right                                                        |


## [Operator Precedence and Associativity](#Operator-Precedence-and-Associativity)
For a complete list of *every* Julia operator's precedence, see the top of this file: [`src/julia-parser.scm`](https://github.com/JuliaLang/julia/blob/master/src/julia-parser.scm). Note that some of the operators there are not defined in the `Base` module but may be given definitions by standard libraries, packages or user code.
You can also find the numerical precedence for any given operator via the built-in function `Base.operator_precedence`, where higher numbers take precedence:
```julia-repl
julia> Base.operator_precedence(:+), Base.operator_precedence(:*), Base.operator_precedence(:.)
(11, 12, 17)

julia> Base.operator_precedence(:sin), Base.operator_precedence(:+=), Base.operator_precedence(:(=))  # (Note the necessary parens on `:(=)`)
(0, 1, 1)
```
A symbol representing the operator associativity can also be found by calling the built-in function `Base.operator_associativity`:
```julia-repl
julia> Base.operator_associativity(:-), Base.operator_associativity(:+), Base.operator_associativity(:^)
(:left, :none, :right)

julia> Base.operator_associativity(:⊗), Base.operator_associativity(:sin), Base.operator_associativity(:→)
(:left, :none, :right)
```
Note that symbols such as `:sin` return precedence `0`. This value represents invalid operators and not operators of lowest precedence. Similarly, such operators are assigned associativity `:none`.


## [Operator Precedence and Associativity](#Operator-Precedence-and-Associativity)
[Numeric literal coefficients](../integers-and-floating-point-numbers/#man-numeric-literal-coefficients), e.g. `2x`, are treated as multiplications with higher precedence than any other binary operation, with the exception of `^` where they have higher precedence only as the exponent.
```julia-repl
julia> x = 3; 2x^2
18

julia> x = 3; 2^2x
64
```
Juxtaposition parses like a unary operator, which has the same natural asymmetry around exponents: `-x^y` and `2x^y` parse as `-(x^y)` and `2(x^y)` whereas `x^-y` and `x^2y` parse as `x^(-y)` and `x^(2y)`.


## [Numerical Conversions](#Numerical-Conversions)
Julia supports three forms of numerical conversion, which differ in their handling of inexact conversions.
-   The notation `T(x)` or `convert(T, x)` converts `x` to a value of type `T`.
    -   If `T` is a floating-point type, the result is the nearest representable value, which could be positive or negative infinity.
    -   If `T` is an integer type, an `InexactError` is raised if `x` is not representable by `T`.
-   `x % T` converts an integer `x` to a value of integer type `T` congruent to `x` modulo `2^n`, where `n` is the number of bits in `T`. In other words, the binary representation is truncated to fit.
-   The [Rounding functions](#Rounding-functions) take a type `T` as an optional argument. For example, `round(Int,x)` is a shorthand for `Int(round(x))`.
The following examples show the different forms.
```julia-repl
julia> Int8(127)
127

julia> Int8(128)
ERROR: InexactError: trunc(Int8, 128)
Stacktrace:
[...]

julia> Int8(127.0)
127

julia> Int8(3.14)
ERROR: InexactError: Int8(3.14)
Stacktrace:
[...]

julia> Int8(128.0)
ERROR: InexactError: Int8(128.0)
Stacktrace:
[...]

julia> 127 % Int8
127

julia> 128 % Int8
-128

julia> round(Int8,127.4)
127

julia> round(Int8,127.6)
ERROR: InexactError: Int8(128.0)
Stacktrace:
[...]
```
See [Conversion and Promotion](../conversion-and-promotion/#conversion-and-promotion) for how to define your own conversions and promotions.


### [Rounding functions](#Rounding-functions)
| Function                                     | Description                      | Return type |
|:---------------------------------------------|:---------------------------------|:------------|
| [`round(x)`](../../base/math/#Base.round)    | round `x` to the nearest integer | `typeof(x)` |
| [`round(T, x)`](../../base/math/#Base.round) | round `x` to the nearest integer | `T`         |
| [`floor(x)`](../../base/math/#Base.floor)    | round `x` towards `-Inf`         | `typeof(x)` |
| [`floor(T, x)`](../../base/math/#Base.floor) | round `x` towards `-Inf`         | `T`         |
| [`ceil(x)`](../../base/math/#Base.ceil)      | round `x` towards `+Inf`         | `typeof(x)` |
| [`ceil(T, x)`](../../base/math/#Base.ceil)   | round `x` towards `+Inf`         | `T`         |
| [`trunc(x)`](../../base/math/#Base.trunc)    | round `x` towards zero           | `typeof(x)` |
| [`trunc(T, x)`](../../base/math/#Base.trunc) | round `x` towards zero           | `T`         |


### [Division functions](#Division-functions)
| Function                                         | Description                                                                                |
|:-------------------------------------------------|:----------------------------------------------------------------------------------------------------------|
| [`div(x, y)`](../../base/math/#Base.div), `x÷y`  | truncated division; quotient rounded towards zero                                                         |
| [`fld(x, y)`](../../base/math/#Base.fld)         | floored division; quotient rounded towards `-Inf`                                                         |
| [`cld(x, y)`](../../base/math/#Base.cld)         | ceiling division; quotient rounded towards `+Inf`                                                         |
| [`rem(x, y)`](../../base/math/#Base.rem), `x%y`  | remainder; satisfies `x == div(x, y)*y + rem(x, y)`; sign matches `x`                                     |
| [`mod(x, y)`](../../base/math/#Base.mod)         | modulus; satisfies `x == fld(x, y)*y + mod(x, y)`; sign matches `y`                                       |
| [`mod1(x, y)`](../../base/math/#Base.mod1)       | `mod` with offset 1; returns `r∈(0, y]` for `y>0` or `r∈[y, 0)` for `y<0`, where `mod(r, y) == mod(x, y)` |
| [`mod2pi(x)`](../../base/math/#Base.Math.mod2pi) | modulus with respect to 2pi; `0 <= mod2pi(x) < 2pi`                                                       |
| [`divrem(x, y)`](../../base/math/#Base.divrem)   | returns `(div(x, y),rem(x, y))`                                                                           |
| [`fldmod(x, y)`](../../base/math/#Base.fldmod)   | returns `(fld(x, y), mod(x, y))`                                                                          |
| [`gcd(x, y...)`](../../base/math/#Base.gcd)      | greatest positive common divisor of `x`, `y`,...                                                          |
| [`lcm(x, y...)`](../../base/math/#Base.lcm)      | least positive common multiple of `x`, `y`,...                                                            |


### [Sign and absolute value functions](#Sign-and-absolute-value-functions)
| Function                                           | Description                                                |
|:---------------------------------------------------|:-----------------------------------------------------------|
| [`abs(x)`](../../base/math/#Base.abs)              | a positive value with the magnitude of `x`                 |
| [`abs2(x)`](../../base/math/#Base.abs2)            | the squared magnitude of `x`                               |
| [`sign(x)`](../../base/math/#Base.sign)            | indicates the sign of `x`, returning -1, 0, or +1          |
| [`signbit(x)`](../../base/math/#Base.signbit)      | indicates whether the sign bit is on (true) or off (false) |
| [`copysign(x, y)`](../../base/math/#Base.copysign) | a value with the magnitude of `x` and the sign of `y`      |
| [`flipsign(x, y)`](../../base/math/#Base.flipsign) | a value with the magnitude of `x` and the sign of `x*y`    |


### [Powers, logs and roots](#Powers,-logs-and-roots)
| Function                                                                    | Description                                                                |
|:----------------------------------------------------------------------------|:---------------------------------------------------------------------------|
| [`sqrt(x)`](../../base/math/#Base.sqrt-Tuple%7BNumber%7D), `√x`             | square root of `x`                                                         |
| [`cbrt(x)`](../../base/math/#Base.Math.cbrt-Tuple%7BAbstractFloat%7D), `∛x` | cube root of `x`                                                           |
| [`hypot(x, y)`](../../base/math/#Base.Math.hypot)                           | hypotenuse of right-angled triangle with other sides of length `x` and `y` |
| [`exp(x)`](../../base/math/#Base.exp-Tuple%7BFloat64%7D)                    | natural exponential function at `x`                                        |
| [`expm1(x)`](../../base/math/#Base.expm1)                                   | accurate `exp(x) - 1` for `x` near zero                                    |
| [`ldexp(x, n)`](../../base/math/#Base.Math.ldexp)                           | `x * 2^n` computed efficiently for integer values of `n`                   |
| [`log(x)`](../../base/math/#Base.log-Tuple%7BNumber%7D)                     | natural logarithm of `x`                                                   |
| [`log(b, x)`](../../base/math/#Base.log-Tuple%7BNumber%7D)                  | base `b` logarithm of `x`                                                  |
| [`log2(x)`](../../base/math/#Base.log2)                                     | base 2 logarithm of `x`                                                    |
| [`log10(x)`](../../base/math/#Base.log10)                                   | base 10 logarithm of `x`                                                   |
| [`log1p(x)`](../../base/math/#Base.log1p)                                   | accurate `log(1 + x)` for `x` near zero                                    |
| [`exponent(x)`](../../base/numbers/#Base.Math.exponent)                     | binary exponent of `x`                                                     |
| [`significand(x)`](../../base/numbers/#Base.Math.significand)               | binary significand (a.k.a. mantissa) of a floating-point number `x`        |


### [Powers, logs and roots](#Powers,-logs-and-roots)
For an overview of why functions like [`hypot`](../../base/math/#Base.Math.hypot), [`expm1`](../../base/math/#Base.expm1), and [`log1p`](../../base/math/#Base.log1p) are necessary and useful, see John D. Cook's excellent pair of blog posts on the subject: [expm1, log1p, erfc](https://www.johndcook.com/blog/2010/06/07/math-library-functions-that-seem-unnecessary/), and [hypot](https://www.johndcook.com/blog/2010/06/02/whats-so-hard-about-finding-a-hypotenuse/).


### [Trigonometric and hyperbolic functions](#Trigonometric-and-hyperbolic-functions)
All the standard trigonometric and hyperbolic functions are also defined:
```julia
sin    cos    tan    cot    sec    csc
sinh   cosh   tanh   coth   sech   csch
asin   acos   atan   acot   asec   acsc
asinh  acosh  atanh  acoth  asech  acsch
sinc   cosc
```
These are all single-argument functions, with [`atan`](../../base/math/#Base.atan-Tuple%7BNumber%7D) also accepting two arguments corresponding to a traditional [`atan2`](https://en.wikipedia.org/wiki/Atan2) function.
Additionally, [`sinpi(x)`](../../base/math/#Base.Math.sinpi) and [`cospi(x)`](../../base/math/#Base.Math.cospi) are provided for more accurate computations of [`sin(pi * x)`](../../base/math/#Base.sin-Tuple%7BNumber%7D) and [`cos(pi * x)`](../../base/math/#Base.cos-Tuple%7BNumber%7D) respectively.
In order to compute trigonometric functions with degrees instead of radians, suffix the function with `d`. For example, [`sind(x)`](../../base/math/#Base.Math.sind) computes the sine of `x` where `x` is specified in degrees. The complete list of trigonometric functions with degree variants is:
```julia
sind   cosd   tand   cotd   secd   cscd
asind  acosd  atand  acotd  asecd  acscd
```


### [Special functions](#Special-functions)
Many other special mathematical functions are provided by the package [SpecialFunctions.jl](https://github.com/JuliaMath/SpecialFunctions.jl).
-   [1](#citeref-1)The unary operators `+` and `-` require explicit parentheses around their argument to disambiguate them from the operator `++`, etc. Other compositions of unary operators are parsed with right-associativity, e. g., `√√-a` as `√(√(-a))`.
-   [2](#citeref-2)The operators `+`, `++` and `*` are non-associative. `a + b + c` is parsed as `+(a, b, c)` not `+(+(a, b), c)`. However, the fallback methods for `+(a, b, c, d...)` and `*(a, b, c, d...)` both default to left-associative evaluation.
------------------------------------------------------------------------


# Complex and Rational Numbers · The Julia Language
Source: https://docs.julialang.org/en/v1/manual/complex-and-rational-numbers/


# [Complex and Rational Numbers](#Complex-and-Rational-Numbers)
Julia includes predefined types for both complex and rational numbers, and supports all the standard [Mathematical Operations and Elementary Functions](../mathematical-operations/#Mathematical-Operations-and-Elementary-Functions) on them. [Conversion and Promotion](../conversion-and-promotion/#conversion-and-promotion) are defined so that operations on any combination of predefined numeric types, whether primitive or composite, behave as expected.


## [Complex Numbers](#Complex-Numbers)
The global constant [`im`](../../base/numbers/#Base.im) is bound to the complex number *i*, representing the principal square root of -1. (Using mathematicians' `i` or engineers' `j` for this global constant was rejected since they are such popular index variable names.) Since Julia allows numeric literals to be [juxtaposed with identifiers as coefficients](../integers-and-floating-point-numbers/#man-numeric-literal-coefficients), this binding suffices to provide convenient syntax for complex numbers, similar to the traditional mathematical notation:
```julia-repl
julia> 1+2im
1 + 2im
```
You can perform all the standard arithmetic operations with complex numbers:
```julia-repl
julia> (1 + 2im)*(2 - 3im)
8 + 1im

julia> (1 + 2im)/(1 - 2im)
-0.6 + 0.8im

julia> (1 + 2im) + (1 - 2im)
2 + 0im

julia> (-3 + 2im) - (5 - 1im)
-8 + 3im

julia> (-1 + 2im)^2
-3 - 4im

julia> (-1 + 2im)^2.5
2.729624464784009 - 6.9606644595719im

julia> (-1 + 2im)^(1 + 1im)
-0.27910381075826657 + 0.08708053414102428im

julia> 3(2 - 5im)
6 - 15im

julia> 3(2 - 5im)^2
-63 - 60im

julia> 3(2 - 5im)^-1.0
0.20689655172413793 + 0.5172413793103449im
```
The promotion mechanism ensures that combinations of operands of different types just work:
```julia-repl
julia> 2(1 - 1im)
2 - 2im

julia> (2 + 3im) - 1
1 + 3im

julia> (1 + 2im) + 0.5
1.5 + 2.0im

julia> (2 + 3im) - 0.5im
2.0 + 2.5im

julia> 0.75(1 + 2im)
0.75 + 1.5im

julia> (2 + 3im) / 2
1.0 + 1.5im

julia> (1 - 3im) / (2 + 2im)
-0.5 - 1.0im

julia> 2im^2
-2 + 0im

julia> 1 + 3/4im
1.0 - 0.75im
```


## [Complex Numbers](#Complex-Numbers)
Note that `3/4im == 3/(4*im) == -(3/4*im)`, since a literal coefficient binds more tightly than division.
Standard functions to manipulate complex values are provided:
```julia-repl
julia> z = 1 + 2im
1 + 2im

julia> real(1 + 2im) # real part of z
1

julia> imag(1 + 2im) # imaginary part of z
2

julia> conj(1 + 2im) # complex conjugate of z
1 - 2im

julia> abs(1 + 2im) # absolute value of z
2.23606797749979

julia> abs2(1 + 2im) # squared absolute value
5

julia> angle(1 + 2im) # phase angle in radians
1.1071487177940904
```
As usual, the absolute value ([`abs`](../../base/math/#Base.abs)) of a complex number is its distance from zero. [`abs2`](../../base/math/#Base.abs2) gives the square of the absolute value, and is of particular use for complex numbers since it avoids taking a square root. [`angle`](../../base/math/#Base.angle) returns the phase angle in radians (also known as the *argument* or *arg* function). The full gamut of other [Elementary Functions](../mathematical-operations/#Elementary-Functions) is also defined for complex numbers:
```julia-repl
julia> sqrt(1im)
0.7071067811865476 + 0.7071067811865475im

julia> sqrt(1 + 2im)
1.272019649514069 + 0.7861513777574233im

julia> cos(1 + 2im)
2.0327230070196656 - 3.0518977991517997im

julia> exp(1 + 2im)
-1.1312043837568135 + 2.4717266720048188im

julia> sinh(1 + 2im)
-0.4890562590412937 + 1.4031192506220405im
```


## [Complex Numbers](#Complex-Numbers)
Note that mathematical functions typically return real values when applied to real numbers and complex values when applied to complex numbers. For example, [`sqrt`](../../base/math/#Base.sqrt-Tuple%7BNumber%7D) behaves differently when applied to `-1` versus `-1 + 0im` even though `-1 == -1 + 0im`:
```julia-repl
julia> sqrt(-1)
ERROR: DomainError with -1.0:
sqrt was called with a negative real argument but will only return a complex result if called with a complex argument. Try sqrt(Complex(x)).
Stacktrace:
[...]

julia> sqrt(-1 + 0im)
0.0 + 1.0im
```
The [literal numeric coefficient notation](../integers-and-floating-point-numbers/#man-numeric-literal-coefficients) does not work when constructing a complex number from variables. Instead, the multiplication must be explicitly written out:
```julia-repl
julia> a = 1; b = 2; a + b*im
1 + 2im
```
However, this is *not* recommended. Instead, use the more efficient [`complex`](../../base/numbers/#Base.complex-Tuple%7BComplex%7D) function to construct a complex value directly from its real and imaginary parts:
```julia-repl
julia> a = 1; b = 2; complex(a, b)
1 + 2im
```
This construction avoids the multiplication and addition operations.
[`Inf`](../../base/numbers/#Base.Inf) and [`NaN`](../../base/numbers/#Base.NaN) propagate through complex numbers in the real and imaginary parts of a complex number as described in the [Special floating-point values](../integers-and-floating-point-numbers/#Special-floating-point-values) section:


## [Complex Numbers](#Complex-Numbers)
```julia-repl
julia> 1 + Inf*im
1.0 + Inf*im

julia> 1 + NaN*im
1.0 + NaN*im
```


## [Rational Numbers](#Rational-Numbers)
Julia has a rational number type to represent exact ratios of integers. Rationals are constructed using the [`//`](../../base/math/#Base.://) operator:
```julia-repl
julia> 2//3
2//3
```
If the numerator and denominator of a rational have common factors, they are reduced to lowest terms such that the denominator is non-negative:
```julia-repl
julia> 6//9
2//3

julia> -4//8
-1//2

julia> 5//-15
-1//3

julia> -4//-12
1//3
```
This normalized form for a ratio of integers is unique, so equality of rational values can be tested by checking for equality of the numerator and denominator. The standardized numerator and denominator of a rational value can be extracted using the [`numerator`](../../base/math/#Base.numerator) and [`denominator`](../../base/math/#Base.denominator) functions:
```julia-repl
julia> numerator(2//3)
2

julia> denominator(2//3)
3
```
Direct comparison of the numerator and denominator is generally not necessary, since the standard arithmetic and comparison operations are defined for rational values:
```julia-repl
julia> 2//3 == 6//9
true

julia> 2//3 == 9//27
false

julia> 3//7 < 1//2
true

julia> 3//4 > 2//3
true

julia> 2//4 + 1//6
2//3

julia> 5//12 - 1//4
1//6

julia> 5//8 * 3//12
5//32

julia> 6//5 / 10//7
21//25
```
Rationals can easily be converted to floating-point numbers:
```julia-repl
julia> float(3//4)
0.75
```
Conversion from rational to floating-point respects the following identity for any integral values of `a` and `b`, except when `a==0 && b <= 0`:


## [Rational Numbers](#Rational-Numbers)
```julia-repl
julia> a = 1; b = 2;

julia> isequal(float(a//b), a/b)
true

julia> a, b = 0, 0
(0, 0)

julia> float(a//b)
ERROR: ArgumentError: invalid rational: zero(Int64)//zero(Int64)
Stacktrace:
[...]

julia> a/b
NaN

julia> a, b = 0, -1
(0, -1)

julia> float(a//b), a/b
(0.0, -0.0)
```
Constructing infinite rational values is acceptable:
```julia-repl
julia> 5//0
1//0

julia> x = -3//0
-1//0

julia> typeof(x)
Rational{Int64}
```
Trying to construct a [`NaN`](../../base/numbers/#Base.NaN) rational value, however, is invalid:
```julia-repl
julia> 0//0
ERROR: ArgumentError: invalid rational: zero(Int64)//zero(Int64)
Stacktrace:
[...]
```
As usual, the promotion system makes interactions with other numeric types effortless:
```julia-repl
julia> 3//5 + 1
8//5

julia> 3//5 - 0.5
0.09999999999999998

julia> 2//7 * (1 + 2im)
2//7 + 4//7*im

julia> 2//7 * (1.5 + 2im)
0.42857142857142855 + 0.5714285714285714im

julia> 3//2 / (1 + 2im)
3//10 - 3//5*im

julia> 1//2 + 2im
1//2 + 2//1*im

julia> 1 + 2//3im
1//1 - 2//3*im

julia> 0.5 == 1//2
true

julia> 0.33 == 1//3
false

julia> 0.33 < 1//3
true

julia> 1//3 - 0.33
0.0033333333333332993
```
------------------------------------------------------------------------


# Strings · The Julia Language
Source: https://docs.julialang.org/en/v1/manual/strings/


# [Strings](#man-strings)
Strings are finite sequences of characters. Of course, the real trouble comes when one asks what a character is. The characters that English speakers are familiar with are the letters `A`, `B`, `C`, etc., together with numerals and common punctuation symbols. These characters are standardized together with a mapping to integer values between 0 and 127 by the [ASCII](https://en.wikipedia.org/wiki/ASCII) standard. There are, of course, many other characters used in non-English languages, including variants of the ASCII characters with accents and other modifications, related scripts such as Cyrillic and Greek, and scripts completely unrelated to ASCII and English, including Arabic, Chinese, Hebrew, Hindi, Japanese, and Korean. The [Unicode](https://en.wikipedia.org/wiki/Unicode) standard tackles the complexities of what exactly a character is, and is generally accepted as the definitive standard addressing this problem. Depending on your needs, you can either ignore these complexities entirely and just pretend that only ASCII characters exist, or you can write code that can handle any of the characters or encodings that one may encounter when handling non-ASCII text. Julia makes dealing with plain ASCII text simple and efficient, and handling Unicode is as simple and efficient as possible. In particular, you can write C-style string code to process ASCII strings, and they will work as expected, both in terms of performance and semantics. If such code encounters non-ASCII text, it will gracefully fail with a clear error message, rather than silently introducing corrupt results. When this happens, modifying the code to handle non-ASCII data is straightforward.


# [Strings](#man-strings)
There are a few noteworthy high-level features about Julia's strings:
-   The built-in concrete type used for strings (and string literals) in Julia is [`String`](../../base/strings/#Core.String-Tuple%7BAbstractString%7D). This supports the full range of [Unicode](https://en.wikipedia.org/wiki/Unicode) characters via the [UTF-8](https://en.wikipedia.org/wiki/UTF-8) encoding. (A [`transcode`](../../base/strings/#Base.transcode) function is provided to convert to/from other Unicode encodings.)
-   All string types are subtypes of the abstract type `AbstractString`, and external packages define additional `AbstractString` subtypes (e.g. for other encodings). If you define a function expecting a string argument, you should declare the type as `AbstractString` in order to accept any string type.
-   Like C and Java, but unlike most dynamic languages, Julia has a first-class type for representing a single character, called [`AbstractChar`](../../base/strings/#Core.AbstractChar). The built-in [`Char`](../../base/strings/#Core.Char) subtype of `AbstractChar` is a 32-bit primitive type that can represent any Unicode character (and which is based on the UTF-8 encoding).
-   As in Java, strings are immutable: the value of an `AbstractString` object cannot be changed. To construct a different string value, you construct a new string from parts of other strings.


# [Strings](#man-strings)
-   Conceptually, a string is a *partial function* from indices to characters: for some index values, no character value is returned, and instead an exception is thrown. This allows for efficient indexing into strings by the byte index of an encoded representation rather than by a character index, which cannot be implemented both efficiently and simply for variable-width encodings of Unicode strings.


## [Characters](#man-characters)
A `Char` value represents a single character: it is just a 32-bit primitive type with a special literal representation and appropriate arithmetic behaviors, and which can be converted to a numeric value representing a [Unicode code point](https://en.wikipedia.org/wiki/Code_point). (Julia packages may define other subtypes of `AbstractChar`, e.g. to optimize operations for other [text encodings](https://en.wikipedia.org/wiki/Character_encoding).) Here is how `Char` values are input and shown (note that character literals are delimited with single quotes, not double quotes):
```julia-repl
julia> c = 'x'
'x': ASCII/Unicode U+0078 (category Ll: Letter, lowercase)

julia> typeof(c)
Char
```
You can easily convert a `Char` to its integer value, i.e. code point:
```julia-repl
julia> c = Int('x')
120

julia> typeof(c)
Int64
```
On 32-bit architectures, [`typeof(c)`](../../base/base/#Core.typeof) will be [`Int32`](../../base/numbers/#Core.Int32). You can convert an integer value back to a `Char` just as easily:
```julia-repl
julia> Char(120)
'x': ASCII/Unicode U+0078 (category Ll: Letter, lowercase)
```
Not all integer values are valid Unicode code points, but for performance, the `Char` conversion does not check that every character value is valid. If you want to check that each converted value is a valid code point, use the [`isvalid`](../../base/strings/#Base.isvalid-Tuple%7BAny%7D) function:
```julia-repl
julia> Char(0x110000)
'\U110000': Unicode U+110000 (category In: Invalid, too high)

julia> isvalid(Char, 0x110000)
false
```


## [Characters](#man-characters)
As of this writing, the valid Unicode code points are `U+0000` through `U+D7FF` and `U+E000` through `U+10FFFF`. These have not all been assigned intelligible meanings yet, nor are they necessarily interpretable by applications, but all of these values are considered to be valid Unicode characters.
You can input any Unicode character in single quotes using `\u` followed by up to four hexadecimal digits or `\U` followed by up to eight hexadecimal digits (the longest valid value only requires six):
```julia-repl
julia> '\u0'
'\0': ASCII/Unicode U+0000 (category Cc: Other, control)

julia> '\u78'
'x': ASCII/Unicode U+0078 (category Ll: Letter, lowercase)

julia> '\u2200'
'∀': Unicode U+2200 (category Sm: Symbol, math)

julia> '\U10ffff'
'\U10ffff': Unicode U+10FFFF (category Cn: Other, not assigned)
```
Julia uses your system's locale and language settings to determine which characters can be printed as-is and which must be output using the generic, escaped `\u` or `\U` input forms. In addition to these Unicode escape forms, all of [C's traditional escaped input forms](https://en.wikipedia.org/wiki/C_syntax#Backslash_escapes) can also be used:
```julia-repl
julia> Int('\0')
0

julia> Int('\t')
9

julia> Int('\n')
10

julia> Int('\e')
27

julia> Int('\x7f')
127

julia> Int('\177')
127
```
You can do comparisons and a limited amount of arithmetic with `Char` values:


## [Characters](#man-characters)
```julia-repl
julia> 'A' < 'a'
true

julia> 'A' <= 'a' <= 'Z'
false

julia> 'A' <= 'X' <= 'Z'
true

julia> 'x' - 'a'
23

julia> 'A' + 1
'B': ASCII/Unicode U+0042 (category Lu: Letter, uppercase)
```


## [String Basics](#String-Basics)
String literals are delimited by double quotes or triple double quotes (not single quotes):
```julia-repl
julia> str = "Hello, world.\n"
"Hello, world.\n"

julia> """Contains "quote" characters"""
"Contains \"quote\" characters"
```
Long lines in strings can be broken up by preceding the newline with a backslash (`\`):
```julia-repl
julia> "This is a long \
       line"
"This is a long line"
```
If you want to extract a character from a string, you index into it:
```julia-repl
julia> str[begin]
'H': ASCII/Unicode U+0048 (category Lu: Letter, uppercase)

julia> str[1]
'H': ASCII/Unicode U+0048 (category Lu: Letter, uppercase)

julia> str[6]
',': ASCII/Unicode U+002C (category Po: Punctuation, other)

julia> str[end]
'\n': ASCII/Unicode U+000A (category Cc: Other, control)
```
Many Julia objects, including strings, can be indexed with integers. The index of the first element (the first character of a string) is returned by [`firstindex(str)`](../../base/collections/#Base.firstindex), and the index of the last element (character) with [`lastindex(str)`](../../base/collections/#Base.lastindex). The keywords `begin` and `end` can be used inside an indexing operation as shorthand for the first and last indices, respectively, along the given dimension. String indexing, like most indexing in Julia, is 1-based: `firstindex` always returns `1` for any `AbstractString`. As we will see below, however, `lastindex(str)` is *not* in general the same as `length(str)` for a string, because some Unicode characters can occupy multiple "code units".


## [String Basics](#String-Basics)
You can perform arithmetic and other operations with [`end`](../../base/base/#end), just like a normal value:
```julia-repl
julia> str[end-1]
'.': ASCII/Unicode U+002E (category Po: Punctuation, other)

julia> str[end÷2]
' ': ASCII/Unicode U+0020 (category Zs: Separator, space)
```
Using an index less than `begin` (`1`) or greater than `end` raises an error:
```julia-repl
julia> str[begin-1]
ERROR: BoundsError: attempt to access 14-codeunit String at index [0]
[...]

julia> str[end+1]
ERROR: BoundsError: attempt to access 14-codeunit String at index [15]
[...]
```
You can also extract a substring using range indexing:
```julia-repl
julia> str[4:9]
"lo, wo"
```
Notice that the expressions `str[k]` and `str[k:k]` do not give the same result:
```julia-repl
julia> str[6]
',': ASCII/Unicode U+002C (category Po: Punctuation, other)

julia> str[6:6]
","
```
The former is a single character value of type `Char`, while the latter is a string value that happens to contain only a single character. In Julia these are very different things.
Range indexing makes a copy of the selected part of the original string. Alternatively, it is possible to create a view into a string using the type [`SubString`](../../base/strings/#Base.SubString). More simply, using the [`@views`](../../base/arrays/#Base.@views) macro on a block of code converts all string slices into substrings. For example:


## [String Basics](#String-Basics)
```julia-repl
julia> str = "long string"
"long string"

julia> substr = SubString(str, 1, 4)
"long"

julia> typeof(substr)
SubString{String}

julia> @views typeof(str[1:4]) # @views converts slices to SubStrings
SubString{String}
```
Several standard functions like [`chop`](../../base/strings/#Base.chop), [`chomp`](../../base/strings/#Base.chomp) or [`strip`](../../base/strings/#Base.strip) return a [`SubString`](../../base/strings/#Base.SubString).


## [Unicode and UTF-8](#Unicode-and-UTF-8)
Julia fully supports Unicode characters and strings. As [discussed above](#man-characters), in character literals, Unicode code points can be represented using Unicode `\u` and `\U` escape sequences, as well as all the standard C escape sequences. These can likewise be used to write string literals:
```julia-repl
julia> s = "\u2200 x \u2203 y"
"∀ x ∃ y"
```
Whether these Unicode characters are displayed as escapes or shown as special characters depends on your terminal's locale settings and its support for Unicode. String literals are encoded using the UTF-8 encoding. UTF-8 is a variable-width encoding, meaning that not all characters are encoded in the same number of bytes ("code units"). In UTF-8, ASCII characters — i.e. those with code points less than 0x80 (128) – are encoded as they are in ASCII, using a single byte, while code points 0x80 and above are encoded using multiple bytes — up to four per character.
String indices in Julia refer to code units (= bytes for UTF-8), the fixed-width building blocks that are used to encode arbitrary characters (code points). This means that not every index into a `String` is necessarily a valid index for a character. If you index into a string at such an invalid byte index, an error is thrown:


## [Unicode and UTF-8](#Unicode-and-UTF-8)
```julia-repl
julia> s[1]
'∀': Unicode U+2200 (category Sm: Symbol, math)

julia> s[2]
ERROR: StringIndexError: invalid index [2], valid nearby indices [1]=>'∀', [4]=>' '
Stacktrace:
[...]

julia> s[3]
ERROR: StringIndexError: invalid index [3], valid nearby indices [1]=>'∀', [4]=>' '
Stacktrace:
[...]

julia> s[4]
' ': ASCII/Unicode U+0020 (category Zs: Separator, space)
```
In this case, the character `∀` is a three-byte character, so the indices 2 and 3 are invalid and the next character's index is 4; this next valid index can be computed by [`nextind(s,1)`](../../base/arrays/#Base.nextind), and the next index after that by `nextind(s,4)` and so on.
Since `end` is always the last valid index into a collection, `end-1` references an invalid byte index if the second-to-last character is multibyte.
```julia-repl
julia> s[end-1]
' ': ASCII/Unicode U+0020 (category Zs: Separator, space)

julia> s[end-2]
ERROR: StringIndexError: invalid index [9], valid nearby indices [7]=>'∃', [10]=>' '
Stacktrace:
[...]

julia> s[prevind(s, end, 2)]
'∃': Unicode U+2203 (category Sm: Symbol, math)
```
The first case works, because the last character `y` and the space are one-byte characters, whereas `end-2` indexes into the middle of the `∃` multibyte representation. The correct way for this case is using `prevind(s, lastindex(s), 2)` or, if you're using that value to index into `s` you can write `s[prevind(s, end, 2)]` and `end` expands to `lastindex(s)`.