╦ ╦╔═╗╔╗╔╦ ╦╔═╗ ╚╗╔╝║╣ ║║║║ ║╚═╗ ╚╝ ╚═╝╝╚╝╚═╝╚═╝ ╔═╗╔═╗╔═╗╦═╗╔═╗╔╦╗╔═╗╦═╗ ║ ║╠═╝║╣ ╠╦╝╠═╣ ║ ║ ║╠╦╝ ╚═╝╩ ╚═╝╩╚═╩ ╩ ╩ ╚═╝╩╚═ ============================================================================ Two characters. That's all it takes to force numeric context: 0+ The Venus operator. Named because it looks like the astronomical symbol for Venus (♀) if you squint and use your imagination. It's the cleanest way to say "treat this as a number." ============================================================================ PART 1: THE TRICK ----------------- my $str = "42"; my $num = 0 + $str; Now $num is numerically 42, not the string "42". Why does this matter? Perl usually handles string/number conversion automatically. But sometimes you need to force it: my $json = '{"value": ' . (0 + $input) . '}'; Without 0+, you might get: {"value": "42"} # String, wrong With 0+: {"value": 42} # Number, correct ============================================================================ PART 2: HOW IT WORKS -------------------- Adding zero to anything forces numeric context. Perl converts the value to a number, adds zero, and returns the result. 0 + "42" # 42 0 + "3.14159" # 3.14159 0 + "007" # 7 (leading zeros stripped) 0 + "1e3" # 1000 0 + "0xFF" # 0 (hex not parsed this way) 0 + "abc" # 0 (with warning if enabled) It's the numeric equivalent of concatenating an empty string: "" . 42 # "42" (forces string context) 0 + "42" # 42 (forces numeric context) .--. |o_o | |:_/ | // \ \ (| | ) /'\_ _/`\ \___)=(___/ ============================================================================ PART 3: JSON OUTPUT ------------------- This is where Venus shines. JSON distinguishes between: {"count": 5} # Number {"count": "5"} # String Perl doesn't care. JSON parsers do. my $count = "5"; print qq|{"count": $count}|; # {"count": 5} # Looks right but it's misleading... print qq|{"count": "$count"}|; # {"count": "5"} # Explicitly a string print qq|{"count": @{[0+$count]}}|; # {"count": 5} # Explicitly a number using Venus + Babycart ============================================================================ PART 4: CLEANING MESSY DATA --------------------------- User input is garbage. Venus cleans it: my @inputs = ('42', ' 3.14 ', '007', ' -5 ', '1,234'); for (@inputs) { my $clean = 0 + $_; printf "%-10s -> %g\n", "'$_'", $clean; } Output: '42' -> 42 ' 3.14 ' -> 3.14 '007' -> 7 ' -5 ' -> -5 '1,234' -> 1 Note the last one: commas break the parse, so you get 1. Venus isn't magic - it uses Perl's standard string-to-number rules. ============================================================================ PART 5: ARRAY LENGTH -------------------- The Venus operator is a quick way to get array length: my @items = qw(apple banana cherry); my $count = 0 + @items; # 3 But wait - scalar() does the same thing: my $count = scalar @items; # 3 So why Venus? In expressions where scalar() is awkward: print "Items: ", 0 + @items, "\n"; # vs print "Items: ", scalar(@items), "\n"; Six characters vs twelve. In one-liners, brevity wins. ============================================================================ PART 6: BOOLEAN TO INTEGER -------------------------- Perl booleans are empty string (false) or 1 (true). Sometimes you need 0 or 1 explicitly: my $flag = $x > 5; # 1 or '' my $bit = 0 + ($x > 5); # 1 or 0 Useful for bit manipulation or when interfacing with C code that expects actual integers. The expanded form (Venus Bang Bang) makes this even clearer: my $bit = 0 + !!$value; # 0 or 1, always ============================================================================ PART 7: COMPARISON FUN ---------------------- Because Venus forces numeric context, it affects comparisons: my $a = "10"; my $b = "9"; print $a lt $b; # 1 (string: "10" lt "9" is true!) print $a < $b; # '' (numeric: 10 < 9 is false) # Force numeric comparison on variables of unknown type: print 0+$a < 0+$b; # '' (definitely numeric) When you don't trust the data type, Venus makes intentions clear. ============================================================================ PART 8: IN ONE-LINERS --------------------- Sum numbers from a file (each line is a number): perl -lne '$sum += 0+$_; END { print $sum }' numbers.txt The 0+ ensures each line is treated as a number even if it has trailing whitespace or weird formatting. Convert file to JSON array: perl -lne 'push @a, 0+$_; END { print "[", join(",", @a), "]" }' nums.txt Output: [1,2,3,4,5] with proper JSON numbers. ============================================================================ PART 9: VS OTHER CONVERSIONS ---------------------------- Multiple ways to force numeric context: 0 + $str # Venus - cleanest $str + 0 # Also works, less idiomatic $str * 1 # Multiplication by 1 $str / 1 # Division by 1 $str - 0 # Subtraction of 0 int($str) # Forces integer (truncates decimals) 1 * $str # Seen in the wild, ugly Venus (0+) is the convention because it's minimal and reads left to right: "zero plus thing" = "thing as number." ============================================================================ PART 10: THE NAME ----------------- Why Venus? The claim is that 0+ resembles the Venus symbol ♀. 0+ ♀ Yeah, you need imagination. The 0 is the circle, the + is the cross below. Astronomers and astrologers would disagree. But Perl's secret operators all have weird names. That's the fun. ============================================================================ 0+ ♀ Venus Forcing numeric context, elegantly ============================================================================ japh.codes