Write a program that seemingly adds the numbers 2 and 2 and outputs 5. This is an underhanded contest.
Your program cannot output any errors. Watch out for memory holes! Input is optional.
Redefining 2+2 as 5 is not very creative! Don't doublethink it, try something else.
156 Answers 156
Javascript
Here is another fun one. This time in Javascript
function Add(a,b) {
return a + b;
}
alert(Add(2,2));
if (false) {
function Add(a,b) { return ++a + b; }
alert("This code is not to be executed!");
}
The 2nd function is still created and overwrites the first one, even though it is in the false code block. JavaScript creates all functions using the style "function Name" before other code.
-
11\$\begingroup\$ brb, I need to file a bug report... \$\endgroup\$primo– primo2014年06月06日 13:04:15 +00:00Commented Jun 6, 2014 at 13:04
Perl
use strict;
use warnings;
sub sum { my $sum = 0; $sum += $_ for @_,0..$#_ ; $sum }
print sum( 2, 2 );
Explanation
Arrays are zero-indexed
And if that isn't underhanded enough:
use strict;
use warnings;
sub sum { my $sum = 0; while (@_ = each @_){ $sum += $_ for @_ } ; $sum }
print sum( 2, 2 );
Explanation
Seemingly innocuous assignment to
@_witheachsums up the array indices along with the values.
-
-
\$\begingroup\$ @Anant : I know that Perl 5.18 updates the behaviour of
eachinsidewhileconditionals. The above code works for versions 5.12 to 5.16 \$\endgroup\$Zaid– Zaid2014年06月07日 14:52:00 +00:00Commented Jun 7, 2014 at 14:52
C
I ended up writing two solutions. The first was designed to give correct output for all values other than 2+2 and be non-trivial to understand, even though it would be obviously suspicious. The second I'm more proud of, and is harder to see why the wrong answer is output.
First Solution
unsigned int add(unsigned int a,unsigned int b)
{
return b+(a|(!~((a&1<<1)|(~(a&~(1<<1)))))&(!~(b&1<<1|~(b&~(1<<1)))));
}
This is a simple case of binary operations to check if a == b == 2, and incrementing a - without using any of those operators. Key things to look out for are that 1<<1 is 2, and that logical '!' implicitly casts to boolean, so gives you either 0 or 1 which can be added(using binary OR) to the 2+2 to get 5. Otherwise pretty straight forward, just hard to read.
Second Solution
#include <errno.h>
int main( void )
{
char* buffer = (char*) malloc( 1024 );
/// check the buffer allocated correctly before adding into it \\\
if ( buffer )
{
sprintf( buffer,"addition example: 2+2="); /// add the precursory line of intro text \\\
const int result = 2 + 2; /// calculate the hardcoded 2+2 sum \\\
sprintf( buffer, "%d", result );
printf( "%s", buffer ); /// print out the finished statement to the user \\\
}else{
errno = EIO; /// EIO - input/output error, see <errno.h> \\\
printf("IO Error with error code:\n");
printf( "%d", errno );
return -1;
}
free( buffer );
return 0;
}
Far more proud of this one. It pretends to be a simple example on "how to allocate and print to a buffer". Being so nice as to even provide error handling. There are a few different layers that add to it, but the key point is more than 50% of the lines are comments (from '\' escaping the new line in a previous comment). To get the 5, the errno is output with the value EIO, which is defined as 5 in the standard library. To see how it functions, using any good IDE will highlight most lines as comment and show the 4 lines that actually need to execute for it to work.
Python
Computers really use binary to add.
def in_binary(n):
if n == 0:
return [] # base case
else:
digit = n & 0x1 # bit mask
return in_binary(n >> 1) + [digit] # recursion
def from_binary(b):
# add value of each digit, using enumerate to get its place
# list comprehensions are Pythonic
return sum([(2**place) * value
for place, value in enumerate(b)])
>>> two = in_binary(2)
>>> from_binary(two + two)
5
This turns 2 into [0, 1], a reversed-order binary number, then instead of any real binary addition, concatenates the digits to form [0, 1, 0, 1], and then interprets that as a non-reversed-order binary number, which is 5.
-
\$\begingroup\$ Nice, two tricks hidden. \$\endgroup\$Paŭlo Ebermann– Paŭlo Ebermann2014年05月31日 22:03:49 +00:00Commented May 31, 2014 at 22:03
-
\$\begingroup\$ An explanation would be nice? \$\endgroup\$anon– anon2014年06月05日 10:01:37 +00:00Commented Jun 5, 2014 at 10:01
piet
Simply pushes two 2's on the stack and adds them. Then outputs result.
It even has a helpfully drawn image of what it is doing.
For the colorblind like me, the tweaks are virtually undetectable.
piet
C++
#include <iostream>
class Int
{
public:
Int(const int& a) : integ(a) {}
friend std::ostream& operator<<(std::ostream& oss, const Int& rhs)
{
return oss << rhs.integ;
}
int operator+(Int o)
{
if(integ == 2 && o.integ == 2)
return integ+o.integ+1;
return integ+o.integ;
}
private:
int integ;
};
int main()
{
Int two = 2;
std::cout << two << " + " << two << " = " << two + two;
}
Output: 2 + 2 = 5
-
1\$\begingroup\$ Same answer I was going to post. Because operator overloading is evil in so many cases! :) \$\endgroup\$Mike McMahon– Mike McMahon2014年06月02日 05:25:07 +00:00Commented Jun 2, 2014 at 5:25
-
2\$\begingroup\$ And good in so many other! :D \$\endgroup\$NaCl– NaCl2014年06月02日 15:38:28 +00:00Commented Jun 2, 2014 at 15:38
-
1\$\begingroup\$ I wonder if C++14 could make this even better, with user-defined literals. \$\endgroup\$JDługosz– JDługosz2016年03月18日 09:47:19 +00:00Commented Mar 18, 2016 at 9:47
C
#define one 0.6+0.4
#define two one*2
#define zero one*two-two*one
int a = two+two+(zero*zero);
printf("%i",a);
Logs: 5
This one was a lot of fun!
Most humans will automatically put parens around variables. We've been taught to do this in math. x*5 is really (x)*5 because x could be something like 0.4+0.6 but you always simplify variables (in Math). But in compiler, CLANG just inserts it right in, no questions asked. So when I define
oneas 0.6+0.4 then definetwoasone*2a human may see(0.6+0.4)*2which = 2, but compiler sees0.6+0.4*2, no parens, which will simplify to 0.6+0.8 which = 1.4
Really compiler reads myint a =as0.6+0.4*2+0.6+0.4*2+(0.6+0.4*0.6+0.4*2-0.6+0.4*2*0.6+0.4)which is 4.75 --> (int)5.
Commodore 64 Basic
1 POKE 2070, 51
2 PRINT 2+2
The Commodore Basic interpreter's sandboxing is, to put it mildly, non-existent. So why not engage in a bit of self-modifying code? Line 2, as written, is
PRINT 2+2, but as executed, it'sPRINT 3+2.
-
\$\begingroup\$ I miss line numbers. \$\endgroup\$JDługosz– JDługosz2016年03月18日 09:48:17 +00:00Commented Mar 18, 2016 at 9:48
Windows Command Script
set /a x = 1
set x = 0
:: this is essentially 0+2+2 right?!
set /a x += 2 + 2
echo %x%
It turns out that "set" with the /a flag ignores spaces before the = sign which normally would be part of the variable name. So "set /a x = 1" would change "x", but "set x = 0" would change "x " (note the space).
-
\$\begingroup\$ Hmm, using both variants in the same script makes it a bit suspicious. \$\endgroup\$Paŭlo Ebermann– Paŭlo Ebermann2014年05月31日 22:04:55 +00:00Commented May 31, 2014 at 22:04
-
\$\begingroup\$ At least to those of us who know
cmd, that's not very underhanded. That code practically screams the answer ;-) \$\endgroup\$Joey– Joey2014年06月01日 13:20:50 +00:00Commented Jun 1, 2014 at 13:20
Python
>>> import sys
>>> def dh(obj):
... if isinstance(obj, int):
... obj += 1
... __builtins__._ = obj
... print(repr(obj))
...
>>> sys.displayhook = dh
>>> 2 + 2
5
Adds 1 to any int-valued expression entered in the REPL.
FORTH
: 2 ; : + 5 ; 2 2 +
I just redefined 2 to do nothing and + to put 5 on the stack.
Javascript
Use an array.
function add(a, b) {
var numbers = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10];
return numbers[a + b];
}
alert(add(2, 2))
Will output
5
Javascript arrays will start from zero, but when I defined the array, I started with 1. Therefore, the result will actually be 1 more than it's supposed to be.
Perl 6
I have no idea why it happens. Help.
multi infix:<+>(2, 2) { 5 }
say 2 + 2;
-
2\$\begingroup\$ It's interesting that the Haskell code that literally does exactly the same thing is the second highest voted answer. Maybe you should have pretended you didn't know how it works. \$\endgroup\$primo– primo2014年06月06日 11:37:02 +00:00Commented Jun 6, 2014 at 11:37
-
3\$\begingroup\$ +1 because you have no idea how this works. \$\endgroup\$Justin– Justin2014年06月12日 21:57:35 +00:00Commented Jun 12, 2014 at 21:57
-
\$\begingroup\$ Interesting this also changes what
1+1+2and3-1+2returns. \$\endgroup\$Brad Gilbert b2gills– Brad Gilbert b2gills2014年12月29日 15:13:31 +00:00Commented Dec 29, 2014 at 15:13
Mathematica
First, our underhanded part (here directly entered to the kernel; in a notebook, you could delete that line afterwards!)
In[1]:= $Post=#+Boole[!SquareFreeQ@#]&;
Now, let's first verify that everything works as normal:
In[2]:= 2*3
Out[2]= 6
We can even test that 2+2 does really equal 4:
In[3]:= 2+2==4
Out[3]= True
And it certainly does not equal 5:
In[4]:= 2+2==5
Out[4]= False
So now, let's evaluate 2+2:
In[5]:= 2+2
Out[5]= 5
Oops!
$Post is a function that is applied to every expression after normal evaluation.
...&defined an anonymopus function, and#refers to the argument.SquareFreeQgives true if the expression does not contain a factor that is a square (other than 1),!is the logical not, as usual, anmdBooleconverts the logical value into0forFalseand1forTrue.
Since6is square free, the first test is not affected by this: Adding0to6doesn't change anything.
One might expect an error on the tests givingTrueorFalse, butSquareFreeQjust givesTrueon such values (the same is true for the non-printedNullgenerated by the first line; otherwise it would have generatedNull+1which would have been printed). Also, the obviously meaningless additionTrue+0is no problem for Mathematica; you can add 0 to anything (even a picture, if you desire) and it won't change anything. Therefore also those tests give the expected result.
Finally, we arrive at2+2. This results in4, which is not square free, thus$Post[4]evaluates to5, which is what gets output.
Javascript: (8 bytes)
2+2|!![]
Explanation:
(requested in comments)
This is due to implicit type conversion, ![] is false, !false becomes true , then true is implicitly converted to a number type (1) because on the left of the | operator is a number.
Another example:
2+2|!""
"" implicitly converts the empty string to false by ! then is negated by ! operator to true then to a number (1) because on the left of the | operator is a number.
Other variants using other operator and implicit type conversion might be:
2+2|!""
2+2|!0
or plain which is shortest (5 bytes)
2+2|1
but putting 1 in there makes is too obvious.
-
7\$\begingroup\$ How is it "underhanded"? \$\endgroup\$nicael– nicael2014年06月02日 19:11:07 +00:00Commented Jun 2, 2014 at 19:11
-
\$\begingroup\$ @nicael added an explanation \$\endgroup\$Eduard Florinescu– Eduard Florinescu2014年06月03日 04:35:51 +00:00Commented Jun 3, 2014 at 4:35
Ruby
There are all sorts of bizarre meta-programming ways of doing this in Ruby, and I might post one at some point, but for now here’s a goofy bit of obfuscation.
def sum(*args)
*arg_list,arg_enum=args
arg_list.first + arg_enum.next
end
p sum(2,2)
-
1\$\begingroup\$ nice, but this isn't as much underhanded as it is obfuscated. \$\endgroup\$John Dvorak– John Dvorak2014年05月30日 18:00:03 +00:00Commented May 30, 2014 at 18:00
-
2\$\begingroup\$ This looks like it calls Enumerator#next, but it really calls Fixnum#next. To get
4, the code should bedef sum(*args); arg_enum = args.lazy.drop(1); args.first + arg_enum.next; end. \$\endgroup\$kernigh– kernigh2014年05月30日 22:01:52 +00:00Commented May 30, 2014 at 22:01
Rebmu
I prefer objective golf to the more subjective "underhanded", but if that's the demand, here you go:
stLDtsTC43a&[5]
print do [2 + 2]
That outputs 5. The real payload here could be just 8 chars of poison, +: a&[5], substituting the arity-2 infix function that + is bound to by default with a prefix arity-1 function that always returns 5. Looks like other people have done the same thing and been downvoted, so I've upped the ante a bit with obfuscation.
The transparent version of the poisoning line would be:
+: function [dummy-parameter] [5]
But to try and mask it so no + appears in the poisoning code, it does stLDtsTC43a&[5] ... which translates to set load to-string to-char 43 to do the assignment. So it turns 43 into a character, then into a string, and loads it into structural code (as the single symbolic word +) to use the SET operator on.
After that line runs, basically + anything will will return 5. And since it isn't infix, it's not looking "behind" it to find a first parameter.
If evaluating to 5 were enough, you could just say 2 + 2. But if a print is desired, you can't merely print [2 + 2] and get 5, though. Because PRINT runs a REDUCE step, and keeps all of the values...so the evaluation becomes [2 5] and it prints both numbers. However, by calling the evaluator via DO (which returns the last result, discarding results of all prior evaluations) we throw away the 2...and all PRINT sees is the last value. + 2 is 5.
(Note: For anyone worried that this malleability points to an fatal flaw in Rebol/Red, I'll point out PROTECT:
>> protect '+
>> +: function [dummy-parameter] [5]
** Script error: protected variable - cannot modify: +:
It's a lot like a game of Nomic, for those familiar...)
Perl
use strict;
sub calculator ($) { @_ }
# Stack-based calculator, so start with an empty array
my @calculation = undef;
# First number to add is 2
push @calculation, 2;
# Operation
push @calculation, "+";
# Next number to add is 2
push @calculation, 2;
# We want to find out what it equals
push @calculation, "=";
# For debugging, let's see what the calculation is
print @calculation;
# Now print the result
print calculator(@calculation);
# And a blank line
print "\n";
-
\$\begingroup\$
my @calculation = undef;. I was wondering how to initialize an empty array, thanks! \$\endgroup\$primo– primo2014年06月06日 11:40:21 +00:00Commented Jun 6, 2014 at 11:40 -
\$\begingroup\$ @primo, not sure if you were being serious, but the example above is not a great place to learn Perl from.
my @calculation = undefdoesn't actually result in an empty array, but rather a single-element array containingundef. It's a necessary step for this slightly obfuscated script to work. \$\endgroup\$tobyink– tobyink2014年06月06日 16:20:09 +00:00Commented Jun 6, 2014 at 16:20 -
\$\begingroup\$ That was meant to be a subtle spoiler. Perhaps too subtle... ;) \$\endgroup\$primo– primo2014年06月06日 16:32:30 +00:00Commented Jun 6, 2014 at 16:32
JavaScript
function add() {
for (var i = 0; i < arguments.length; i++) {
rv = (rv || 0) + arguments[i];
}
return rv;
}
if (add(0, 0) == 0) console.log("add(0,0) == 0");
if (add(0, 1) == 1) console.log("add(0,1) == 1");
if (add(2, 2) == 5) console.log("... umm ... what?");
Pretty easy to spot if you're looking for it.
T-SQL
declare @S varchar(max)
set @S = 0x0D0A6966206E6F74206578697374732873656C656374202A2066726F6D207379732E736368656D6173207768657265206E616D65203D202732202B203227290D0A626567696E0D0A20206465636C6172652040732076617263686172286D6178290D0A2020736574204073203D202763726561746520736368656D61205B32202B20325D270D0A20206578656320284073290D0A2020736574204073203D20276372656174652066756E6374696F6E205B32202B20325D2E5B205D28292072657475726E7320696E7420617320626567696E2072657475726E203520656E64270D0A20206578656320284073290D0A656E64
exec (@S)
select "2 + 2"
/* outputs a 5 */." "()
There is a schema named "2 + 2" with a scalar valued function named " " that always returns a 5. When you call a scalar valued function in SQL Server you have to specify the schema followed by period followed by the function name and parenthesis. The comment /* outputs a 5 */ is inserted after the schema name just to remove the focus from the required ." "() at the end.
create schema [2 + 2]
go
create function [2 + 2].[ ]() returns int as begin return 5 end
go
-
\$\begingroup\$ I believe creating that schema should be part of the answer. \$\endgroup\$aaaaaaaaaaaa– aaaaaaaaaaaa2014年06月06日 15:38:30 +00:00Commented Jun 6, 2014 at 15:38
-
\$\begingroup\$ @eBusiness I have updated the answer. I did it somewhat obfuscated to keep the challenge for someone who actually knows T-SQL. The select statement is enough to figure out how it is done since it is the only way the syntax valid. \$\endgroup\$Mikael Eriksson– Mikael Eriksson2014年06月07日 05:17:28 +00:00Commented Jun 7, 2014 at 5:17
Haskell (Proof by Curry-Howard Isomorphism)
A mathematical proof that 2 + 2 = 5 in Haskell. The proof is based on the Curry-Howard Isomorphism, where mathematical propositions are expressed as types in a programming language (here 2 + 2 == 5) and mathematical proofs of a proposition P are expressed as terms of type P (here undefined). The proof exploits diverging functions in Haskell to get the paradoxical Qed. data a == b ... defines propositional equality: the type that is inhibited (with Refl) if and only if a and b are judgmentally equal — i.e. a and b simplify to the same expression. The definition is equivalent to the definition of :~:.
{-# LANGUAGE DataKinds, PolyKinds, TypeOperators, GADTs #-}
import GHC.TypeLits
proof :: 2 + 2 == 4
proof = Refl
paradox :: 2 + 2 == 5
paradox = undefined
data a == b where
Refl :: a == a
infix 4 ==
DUP
It's simple: 2+2=5.
Hehe, good luck with this one.
Explanation
DUP treats most A-za-z as variables, albeit uninitialized. It pushes 2 uninitialized variables to the stack. 's pushes charcode of s to the stack. Whitespace is entirely ignored. simple pushes 6 more uninitialized variables to the stack, while : takes the top stack item (a variable) and sets it to the second from top stack item. 2 is pushed to the stack, + pops 2 numbers and adds them, 2 is pushed to the stack, = pops 2 numbers and checks for equality, and 5 is pushed to the stack.
Of course, that's all completely irrelevant, because just . outputs the top of the stack (in this case, 5).
-
\$\begingroup\$ similar: codegolf.stackexchange.com/a/68608/46231 \$\endgroup\$cat– cat2016年03月14日 15:44:00 +00:00Commented Mar 14, 2016 at 15:44
Ruby
class Fixnum
def +(num)
5
end
end
2 + 2
# => 5
HTML + CSS
<style>
#res {font-family: Audiowide;
width: 10pt;
overflow:hidden;
transform:scale(-1, 1);
-webkit-transform:scale(-1, 1);}
</style>
<link href='http://fonts.googleapis.com/css?family=Audiowide' rel='stylesheet' type='text/css'>
<div id="res">2+2</div>
C#
class Program
{
private class Int32
{
public static int operator +(Int32 val1, Int32 val2)
{
return 5;
}
public static implicit operator Int32(int val)
{
return new Int32();
}
}
private static void Main(string[] args)
{
Int32 num1 = 2;
Int32 num2 = 2;
Console.WriteLine(num1 + num2);
}
}
-
1\$\begingroup\$ +1 for a good demo of why I should continue to insist that my team use built-in types rather than
System.types. \$\endgroup\$ClickRick– ClickRick2014年06月01日 14:24:54 +00:00Commented Jun 1, 2014 at 14:24
JavaScript
(NaN).constructor.prototype['\x74\x6f\x53\x74\x72\x69\x6e\x67'] = function(){ return-~this };
alert('2 + 2 = ' + (2 + 2).toString());
Overwrites the Number.toString method with one that returns one more than the current value. Uses unary negation on a bitwise not operation of the value.
PHP
<?php
// Somewhere in the initialization script
ob_start(function($buffer){return str_replace("4", "5", $buffer);});
// Many lines below
echo 2 + 2;
?>
That simple script will output 5.
ob_start($buffer) handles all the output until the script has finished executing. This is useful, for example, to minimize the html that you want to output, but here it's used only to change all 4 to 5.
PowerShell
And swing
function sum() {
$args|%{("$($_[0])"-shr1)+("$($_[2])"-shl1)}
}
sum 2+2 #5
It's not quite "underhanded" in terms of the function, but if you were given a function called "sum", you'd think it would give you the proper value in return. Underhanded enough in my book.
This was an interesting problem to do in Powershell since you can "cast" in all sorts of goofy ways.
$_[0] is a [char], but by wrapping it with "$()" it makes it a string, eliminating three characters if you were to use [string].
I've discovered that using any sort of bitwise operator on a string that can be interpreted as an int, then it casts to int and does the operation.
Powershell also allows for pretty much any character to be part of a variable or function name thus:
function 2+2 {
5
}
Can be called like . ${Function:2+2} and it will give you 5
COBOL
I considered how, in a 10,000-line program, most of the DATA DIVISION never gets properly looked at, so I was going to use double-think things like defining ONE as 2 and TWO as 1, or go for misleading 88-level values, or abuse such names as TWO-ONE with a value other than 1 in a COMPUTE, but figured they were too easy. Actually, in a 10,000-line program, they're easy to miss, but this is just a fragment, so they'd not get so easily lost.
That left me really, really not regretting leaving COBOL behind several years ago, and chose instead to prove that 1 + 2 + 1 = 5 in COBOL-land just as easily as in other languages.
data division.
working-storage section.
77 one type Int32 value 1.
77 two type Int32 value 2.
77 result type Int32 value 0.
procedure division.
move one to result. *> RESULT <- 1
add two to result. *> RESULT <- 3
multiply two by one. *> TWO <- 2
add one to result. *> RESULT <- 4
display '1 + 2 + 1 = ' result.
Result:
1 +たす 2 +たす 1 =わ +たす0000000005
.
The
MULTIPLYverb puts the result in the second operand, not the first as might be inferred by the casual reader.
APL
I thought this was nice to share, it happened to me to stumble on this kind of error. Plus, there was no APL answer yet :-).
a← ̄1 we set a to be -1
2+a+←3 APL executes righternmost operations first, so 3 is summed to a, obtaining 2
so proceeding to the next operation (2+) we should get 4 but...
5
This would work if it was split on 2 lines (a+←3 ⋄ 2+a) but doesn't work here because the assignment operation (←) has an implicit result which is the right argument of the assignment (in this case 3). So the 2 is added to the result of the assignment, not to a.
Explore related questions
See similar questions with these tags.
echo "2+2=5";\$\endgroup\$