# Find i^n, given n

The Challenge

In as few characters as possible, find the value of $$\i^n\$$, given $$\n\$$, a positive integer greater than 0. This should be outputted as a String.

For those that don't know, $$\i\$$ is defined such that $$\i^2=-1\$$. So:

• $$\i^1=i\$$
• $$\i^2=-1\$$
• $$\i^3=-i\$$
• $$\i^4=1\$$

This then repeats..

Rules

• If your language supports complex numbers, don't use any functions or arithmetic that could work this out.
• Floating point inaccuracies are fine for answers that would return decimals anyway, but integer inputs should give exact results

Bonus Points

-5 if you can work the value out where n is also negative

-15 if you can work out the value for any real number (this bonus includes the -5 from the above bonus)

Good luck!

• In what format do we return exactly? Through function output or stdout? Nov 21, 2014 at 15:59
• @MartinBüttner but if i choose function output, how should the output should be formatted/stored without native complex numbers in my language? Nov 21, 2014 at 16:02
• @BetaDecay What are floating point integers? o.O Nov 21, 2014 at 18:04
• @MartinBüttner Haha wrong word :/ Floating point number then Nov 21, 2014 at 18:17
• I feel so stupid. I only just realized that python has a built in complex type. Nov 22, 2014 at 6:03

# Perl 6, 19 bytes - 5 = 14

{<1 i -1 -i>[$_%4]}  The result of % has the same sign as the divisor in this language. Try it online! # C (gcc), 30 bytes f(x){printf(L"iㄭ椭1"+x%4);}  Try it online! # C (gcc), 44 bytes -15=29 #define f(x)cos(x*acos(0))+1i*sin(x*acos(0))  Try it online! Handles signed and noninteger arguments. # R, (29 bytes -15) = 14 cos(m<-scan()*pi/2)+sin(m)*1i  Try it online! Conventional complex number output; works for negative and real inputs. (for completeness, there is also c(1,scan()*90) for a score of -1, using blutorange's dubious inventive polar output format in degrees) • Based on "(this bonus includes the -5 from the above bonus)", I don't think you can include both the -5 and -15 bonuses Oct 30, 2020 at 15:32 • @EthanChapman Ah, yes, you're right. Fixed. I was wondering why nobody else had such a good bonus... Oct 30, 2020 at 15:33 # Rust34 33 bytes fn main() { // closure: // |n:usize|["1","i","-1","-i"][n%4] // call with: print!("{}", (|n:usize|["1","i","-1","-i"][n%4])(3)); }  Try it online! The closure itself: |n:usize|["1","i","-1","-i"][n%4]  • You should probably put a version without comments and whitespace here as well, so it's easier to see what the actual 34 byte program is. Apr 7, 2021 at 20:51 # Haskell, 29 bytes - 5 = 24 f n=words"1 i -1 -i"!!mod n 4  Works for negative powers. I had a pointfree version worked out, but it turns out it's actually longer. f=(words"1 i -1 -i"!!).(mod4)  ## Clojure (6454 31 chars) (defn i2n[n](println(case(mod n 4) 1 "i" 2 "-1" 3 "-i" 0 "1")))  ## Edit Per @SeanAllred's suggestion, here's a version which uses a literal vector instead of a case function: (defn i2n[n](println (["1" "i" "-1" "-i"] (mod n 4))))  ## Edit 2 By counting on the REPL to print out the resultant collection and coding the function using the #() shortcut we can reduce it to #(["1" "i" "-1" "-i"](mod % 4))  (Which is actually much more Clojure/Lisp-ish as the function now actually returns the generated result, allowing the function to be used with map, as in (map #(["1" "i" "-1" "-i"](mod % 4)) [0 1 2 3 4 5 6 7 8])  which prints ("1" "i" "-1" "-i" "1" "i" "-1" "-i" "1")  Share and enjoy. • Instead of using a select structure, can't you use some sort of explicit array as in my answer? Nov 24, 2014 at 1:22 # Groovy: 27-5 = 22 f={n->[1,'i',-1,'-i'][n%4]}  ## C 105, was 117 char c[2]; int main() { int n,i,j=0;scanf("%d",&n);i=n%4; i>1?c[j++]='-':c[j+1]='\0'; c[j]=i&1?'i':'1'; puts(c); }  • It doesn't even compile because you must parenthesize the assignments after : in ?: statements in plain C. Also, what's the point of using 0==0 when you can use single char 1? And no need in parentheses before ?. Also, the last ?: statement could be shortened to c[j]=i&1?'i':'1';. Nov 23, 2014 at 14:20 • @Ruslan In CodeBlocks Mingw there is only 1 warning around i&0. i&0==0 is a test for even, if i is even the result is 0 else it is 1. Nov 25, 2014 at 6:13 • Yeah, but what's the point of using 0==0 when it's identical to 1? Note that == has higher precedence than &, otherwise your (supposed) test of (i&0)==0 would always be true. Nov 25, 2014 at 6:18 # Ruby, 208 - 15 = 193 p=Math::PI/2;t=gets.to_f*p;l=->n{Math::cos(n).round(2)};k=l.call(t);if k!=0;k=k.to_i if k.abs==1;print k;end;m=l.call(t+p);if m!=0;r="i";r='-'+r if m==-1;r="#{m}"+r if 1>m && -1<m;r=" + "+r if k!=0;puts r end  This implementation completely conforms to the spec! 1.0 is written as 1, -1.0i is written as -i, etc. I don't see any other solution that incorporates this along with supporting floating points, except for maybe the TI-Calculator. Ungolfed: p=Math::PI/2 t=gets.to_f*p l=->n{Math::cos(n).round(2)} k=l.call(t) if k!=0 k=k.to_i if k.abs==1 print k end m=l.call(t+p) if m!=0 r="i" r='-'+r if m==-1 r="#{m}"+r if 1>m && -1<m r=" + "+r if k!=0 puts r end  • l.call(t)l[t]. Read Tips for golfing in Ruby for more. Dec 4, 2015 at 6:43 # C, 61 main(n){scanf("%d",&n);printf("%c%c",n%4/2*45,n%4%2?'i':49);}  Try it here. # PARI/GP, 26 - 5 = 21 n->Str([1,I,-1,-I][n%4+1])  n->cos(t=Pi*n/2)+I*sin(t) is one character shorter, but doesn't handle exact answers. Of course n->I^n is disallowed, and presumably also PARI's powIs. # Java (OpenJDK 8), 39 bytes n->new String[]{"1","i","-1","-i"}[n%4]  Try it online! # Haskell, 27 bytes (cycle(words"1 i -1 -i")!!)  Try it online! # 05AB1E, 12 bytes ®sfgm¹Éi1'i:  Try it online! ® # Push -1 onto the stack. sfg # Push the number of prime factors of input. m # -1^(number_prime_factors) ¹Éi # is input even? 1'i: # if input was even, replace 1 with i.  # Forth (gforth), 53 bytes - 5 bytes (bonus) = 48 bytes : f 4 mod dup 1 > if ." -"then 2 mod 56 * '1 + emit ;  Try it online! This works for both positive and negative numbers ### Code Explanation : f \ start a new word definition 4 mod dup \ get result of n % 4 (and make a copy) 1 > if \ if result is 2 or 3 ." -' \ print a minus sign then \ end the if 2 mod 56 * \ get result modulo 2 and multiply by 56 (difference between ascii for '1' and 'i') '1 + \ add to ascii value of '1' emit \ output the character for the given value ; \ end the word definition  # Zsh, 30 bytes, score 25 (-5) a=({,}{,-}{1,i}) <<<$a[$1%4+5]  Try it online! Based on the bash answer, but with some changes needed: • %4 results in a value in the range -3 to 3 (negative inputs give negative outputs), so we shift up with +5. • Arrays are 1-indexed, hence +5 instead of +4. • We make our array twice as long by using brace expansion: {,}foo expands to foo foo. # Tcl, 50 bytes proc I n {expr$n%4==3?"-i":$n%4==2?-1:$n%4?"i":1}


Try it online!

• Input is in A1
• B1: A1/2*PI(
• Result: =COMPLEX(COS(B1),SIN(B1

# Stax, 9 - 5 = 4 bytes

ü▲τ}εT├?á


Run and debug it

# Branch, 38 bytes

^\4^%/;c1^>/0c45^?[.0]anc2^%/49c105^?.


Try it on the online Branch interpreter!

## Explanation

      Implicit - the initial node's value is set to the first argument
^\4   Create a parent and sibling and set the right child to 4
%     Modulo
/;    Go to the left child and copy the mod result
c1    Go to the right child (automatically assigned register C) and set it to 1
>     1 if the mod result is greater than 1, 0 otherwise
/0    Go to the left child and set to 0
c45   Go to the right child and set it to 45 (codepoint for "-")
?     Conditional - if the mod was greater, go to the right child (45), and left child (0) otherwise
[  ]  While the value isn't 0
.    Output it
0   And set it to zero (this is basically an if statement)
an    Go to the left child and load the first argument (register N by default)
c2    Go to the right child and set it to 2
%     Modulo
/49   Go to the left child and set it to 49 (codepoint for "1")
c105  Go to the right child and set it to 105 (codepoint for "i")
^     Go to the parent
?     Conditional - if the exponent was even, go left, otherwise, go right
.     Output


# Lua, 33 - 5 = 28 bytes

print(({1,'i',-1,'-i'})[...%4+1])


Try it online!

# Go, 75 57 bytes, no bonus

func(n int)string{return[]string{"1","i","-1","-i"}[n%4]}


Try it online!

if n<0{n=4+n} is included here because the % operator in Go returns negative if the dividend is negative.

• At the moment, this qualifies for a -5 bonus (since it handles negative numbers too), so your score is 70 bytes. But, if you don't go for any bonuses, you can get this down to 58 bytes Jul 8 at 18:15
• You can also remove the redundant newline for 57 bytes Jul 8 at 19:17

# C# 63-5 = 58

public string m(int n)=>n%2==0?(n%4==0?"1":"-1"):(m(n-1)+"i");

• output is in form -1i, 1i, i, or 1 Nov 23, 2014 at 23:38
• You cannot claim the -15 bonus as this would fail on the input 3.247104. You may only claim the -5 bonus. Nov 24, 2014 at 7:06
• Oh, sorry, yes - I didn't read the bonuses bit properly Nov 27, 2014 at 3:34

# Keg, 15 - 5 = 10 bytes

1i0;-i¿4%⊙&ø&


Try it online!

Pushes the four different possibilities and then takes the input modulo 4 and indexes the stack.

• You program supports negative numbers, you should have the -5 bonus! -5 if you can work the value out where n is also negative
– user85052
Nov 16, 2019 at 6:09

# Vyxal, r, 5 - 15 = -10 bytes

90*1"


Try it Online!

Well if the Ruby answer's output method is valid, so is this. Outputs in "polar form (angular unit: degrees)".

## Explained

90*1"
90*   # Multiply the input by 90
1" # Push one and pair the two inputs. The -r flag makes dyads take their arguments in reverse.


# Thunno 2, 10 - 5 = 5 bytes

-iu'i1K$i  Attempt This Online! Port of Kevin Cruijssen's 05AB1E answer. #### Explanation -iu'i1K$i  '# Implicit input
-i          # Push the string "-i"
u         # Push the number -1
'i      '# Push the string "i"
1      # Push the number 1
K     # Wrap the stack into a list
# -> [1, "i", -1, "-i"]
\$i   # Index the input in
# (0-based, modular)
# Implicit output
`