LinuxCommandLibrary

double-bracket

TLDR

Test condition (bash/zsh extended)

$ [[ -f [file] ]] && echo "exists"
copy
Pattern matching
$ [[ "[string]" == pattern* ]]
copy
Regex matching
$ [[ "[string]" =~ ^[0-9]+$ ]]
copy
Safe variable comparison (no quoting needed)
$ [[ $var == "value" ]]
copy
Combine conditions
$ [[ -f [file] && -r [file] ]]
copy

SYNOPSIS

[[ expression ]]

DESCRIPTION

[[ is bash/zsh's enhanced conditional expression. It provides safer and more powerful tests than [.
Key advantages over [:
- No word splitting on variables (unquoted $var is safe)
- Pattern matching with == and !=
- Regular expression matching with =~
- && and || work inside the brackets
- < and > don't need escaping

$ # Pattern matching
[[ $file == *.txt ]] && echo "text file"

# Regex matching
if [[ $email =~ ^[A-Za-z]+@[A-Za-z]+\.[A-Za-z]+$ ]]; then
    echo "Valid email format"
fi

# No quoting needed
[[ $var == "test" ]]  # Safe even if var is empty
copy

OPERATORS

File tests: Same as [ (-f, -d, -e, -r, -w, -x, etc.)
String comparison:
- == or =: Pattern match (glob)
- !=: Not pattern match
- =~: Regex match
- <, >: Lexicographic order
Numeric: -eq, -ne, -lt, -le, -gt, -ge
Logical:
- &&: AND
- ||: OR
- !: NOT

CAVEATS

[[ is bash/zsh specific, not POSIX. Use [ for portable scripts.
Regex with =~ uses ERE (Extended Regular Expressions). Captured groups go in BASH_REMATCH array.
Quote the right side of == to match literally: **[[ $x == "pattern*" ]]** matches the literal string.
Don't quote regex patterns: [[ $x =~ ^test ]] not [[ $x =~ "^test" ]]

SEE ALSO

test(1), bash(1), zsh(1)

Copied to clipboard