Test a number for narcissism

53

6

A Narcissistic Number is a number which is the sum of its own digits, each raised to the power of the number of digits.

For example, take 153 (3 digits):

13 + 53 + 33 = 1 + 125 + 27 = 153

1634:

14 + 64 + 34 + 44 = 1 + 1296 + 81 + 256 = 1634

The Challenge:

Your code must take input from the user and output True or False depending upon whether the given number is a Narcissistic Number.

Error checking for text strings or other invalid inputs is not required. 1 or 0 for the output is acceptable. Code that simply generates a list of Narcissistic Numbers, or checks the user input against a list, does not qualify.

OEIS A005188

Iszi

Posted 2013-11-14T01:55:37.983

Reputation: 2 369

3Is it ok if I output True if it's such a number, but anything else (in this case the number itself) if not? – devRicher – 2017-01-06T21:51:55.527

Answers

39

APL (15)

∆≡⍕+/(⍎¨∆)*⍴∆←⍞

Outputs 1 if true and 0 if false.

Explanation:

  • ∆←⍞: read a line (as characters), store in
  • (⍎¨∆)*⍴∆: evaluate each character in and raise it to the power ⍴∆
  • ∆≡⍕+/: see if the input equals the string representation of the sum of these

marinus

Posted 2013-11-14T01:55:37.983

Reputation: 30 224

9what did i just read – Jbwilliams1 – 2014-02-18T20:13:51.170

4@LagWagon God's language – tomsmeding – 2014-07-08T08:00:39.057

21

GolfScript, 16 characters

~.`:s{48-s,?-}/!

Input must be given on STDIN, output is 0 or 1 indicating non-narcissistic / narcissistic number.

Explanation of the code:

~              # Evaluate the input to get a number
.              # Accumulator (initially the number itself)
`:s            # Convert number to string and assign to variable s
{              # Loop over characters of the string
  48-          # Reduce character value by 48
  s,           # Push length of input number
  ?            # Power
  -            # Subtract result from accumulator
}/
!              # Not! (i.e. iff accumulator was zero it was a narcissistic number)

Howard

Posted 2013-11-14T01:55:37.983

Reputation: 23 109

I did a double-take on ~.` but it seems impossible to improve. Nice one. – Peter Taylor – 2013-11-20T17:28:30.460

15

Mathematica, 43 chars

Tr[#^Length@#&@IntegerDigits@#]==#&@Input[]

alephalpha

Posted 2013-11-14T01:55:37.983

Reputation: 23 988

14

Perl, 38 characters

perl -lpe '$@=y///c;$s+=$_**$@for/./g;$_=$_==$s'

A pretty straightforward implementation.

Here's a slightly different version that fits in 35 characters:

perl -lpe '$@=y///c;$s+=$_**$@for/./g;$_-=$s'

This version outputs a false value if the input is narcissistic, otherwise it outputs a (Perl-accepted) true value. One might argue that this backwards version falls within the limits of the challenge description, but upon reflection I decided not to. I'm not that desperate to improve my score. Yet.

breadbox

Posted 2013-11-14T01:55:37.983

Reputation: 6 893

Same idea but shorter: perl -pe'map$s+=$_**@y,@y=/./g;$_=$_==$s' – msh210 – 2016-06-19T07:48:57.263

“Error checking for text strings or other invalid inputs is not required.” – So why not suppose the input will be valid number, without trailing newline? echo -n 153 | perl -pe '…' will work without -l. – manatwork – 2013-11-14T12:26:54.777

I think so long as you define what your true and false outputs are, it should be legal – Cruncher – 2013-11-14T16:48:18.917

Strictly speaking, the wording of the challenge text does leave a bit of ambiguity as to what True/False or 0/1 should mean, so I'll let this one pass. A different script of equal length that returns true for narcissistic values would have the advantage, though. – Iszi – 2013-11-14T20:47:47.033

13

J, 23 chars

(".=+/@("."0^#))(1!:1)1

(1!:1)1 is keyboard input (returning a string).

". converts input to a number; "0 specifies a rank (dimension) of 0, in other words, taking each character and converting it to a number.

^ is the power function and # is the length function, thus taking each digit to the power of the length of the string (equivalently, the number of digits).

+/ is just sum, and = is comparing the sum and number.

rationalis

Posted 2013-11-14T01:55:37.983

Reputation: 456

2"Your code must take input from the user and output True or False depending upon whether the given number is a Narcissistic Number." (emphasis mine) – John Dvorak – 2013-11-14T04:45:18.593

@JanDvorak My bad -- added keyboard input. – rationalis – 2013-11-14T06:08:23.013

12

Ruby, 34+5=39

With command-line flags

ruby -nlaF|

Run

p eval [$F,0]*"**#{~/$/}+"+"==#$_"

Outputs true or false.

histocrat

Posted 2013-11-14T01:55:37.983

Reputation: 20 600

3This may be the most Ruby flags I've ever seen in a legitimate code golf :P – Doorknob – 2013-11-21T21:24:42.080

11

R, 71 69 66 56 48

Reduced by 8 bytes thanks to @Giuseppe! The idea was to perform the integer division before the modulo operation.

i=nchar(a<-scan()):0;a==sum((a%/%10^i%%10)^i[1])

(3-year) old version with corresponding explanation:

i=nchar(a<-scan()):1;a==sum(((a%%10^i)%/%10^(i-1))^i[1])

a<-scan() takes a number (integer, real,...) as input (say 153 for the example).
i becomes a vector containing 3 to 1 (the number of characters of a being 3).
%% is vectorized so a%%10^i means a modulo 1000, 100 and 10: it therefore gives 153, 53, 3.
(a%%10^i)%/%10^(i-1) is the integer division of that vector by 100, 10, 1: therefore, 1, 5, 3.
We elevate that with the first element of i which is the number of characters (here digits) of a, i. e. 3, thus giving a vector containing 1, 125, 27 that we sum and compares to a.

plannapus

Posted 2013-11-14T01:55:37.983

Reputation: 8 610

Does the integer division always round down? Otherwise, you could run into problems with e.g. 370 (a narcissistic number) turning into 4,7,0 (which would return false) or 270 (non-narcissistic) turning into 3,7,0 (returning true). – Iszi – 2013-11-14T20:40:46.543

Integer division doesn't round... The integer division of 370 by 100 is 3 with the remainder of 70 and not 3.70. – plannapus – 2013-11-15T07:40:47.777

148 bytes...somebody bumped this to the homepage! – Giuseppe – 2017-09-01T19:55:37.917

9

Python 3, 56 bytes

Not very obfuscated, but a simple solution.

s = input()
print(int(s)==sum(int(c)**len(s)for c in s))

danmcardle

Posted 2013-11-14T01:55:37.983

Reputation: 695

Fixed your byte count. Also, you can remove those 2 spaces on the first line. – mbomb007 – 2016-11-08T15:39:17.283

1The [ and ] are unnecessary, and you can drop the space in front of for too, so: sum(int(c)**len(s)for c in s) – marinus – 2013-11-14T07:12:40.930

That's awesome! Thanks for the tip. – danmcardle – 2013-11-14T12:05:28.137

1You can save two characters by removing the spaces in s = input() and another one by moving this to 2.7 where print isn't a function. – Ben – 2013-11-16T17:31:46.367

Good point, edited. – danmcardle – 2013-11-17T05:32:37.297

I think you should point out that adding braces to print (hence one character more) would make this a valid Python 2.x and Python 3.x solution. – Martin Thoma – 2013-11-18T18:24:36.210

In Python 2.7 first row must by s=raw_input() – AMK – 2013-11-18T19:16:33.953

You're absolutely right. Rather than add the four characters, I'll just switch it back to Python3 where it was 57 chars. – danmcardle – 2013-11-21T02:35:22.557

Was workin on the same approach:( – Eduard Florinescu – 2014-01-09T20:02:56.767

Wouldn't lambda s:int(s)==sum(int(c)**len(s)for c in s) work? – MilkyWay90 – 2019-04-23T23:45:34.523

You can actually get 43 bytes using Python 2

– MilkyWay90 – 2019-04-23T23:50:42.127

8

PHP, 80 74 66 chars

Very straightforward PHP solution:

<?for(;$i<$l=strlen($a=$argv[1]);)$s+=pow($a[$i++],$l);echo$s==$a;

It assumes error_reporting doesn't include notices, otherwise quite a few extra characters will be needed to initialize $s=0; and $i=0.

Thx @manatwork for shortening many chars.

Vlad Preda

Posted 2013-11-14T01:55:37.983

Reputation: 181

Don't assign $a and $l in separate statements. <?for($i=0;$i<$l=strlen($a=$argv[1]);$i++){$s+=pow($a[$i],$l);}echo$s==$a; is shorter. – manatwork – 2013-11-14T14:58:45.573

As you already have a statement which generate a notice, just add another: remove the loop control variable initialization. Incrementing the loop control variable also not need to be a standalone statement. And the braces are definitely not needed: <?for(;$i<$l=strlen($a=$argv[1]);)$s+=pow($a[$i++],$l);echo$s==$a;. – manatwork – 2013-11-14T15:09:29.527

@manatwork: Thank you for the warm welcome to codegolf :) – Vlad Preda – 2013-11-14T15:13:31.767

Can be golfed to this for(;$i<$l=strlen($a=$argn);)$s+=$a[$i++]**$l;echo$s==$a; – Jörg Hülsermann – 2017-05-17T16:51:00.303

8

K, 24 23

{x=+/xexp["I"$'a]@#a:$x}

Shaved 1 char with reordering

{x=+/{x xexp#x}"I"$'$x}

tmartin

Posted 2013-11-14T01:55:37.983

Reputation: 3 917

8

Dc: 48 characters

[1pq]Sr?d0rdZSz[d10/r10%lz^rSh+Lhd0!=c]dScx+=r0p

Sample run:

bash-4.1$ dc -e '[1pq]Sr?d0rdZSz[d10/r10%lz^rSh+Lhd0!=c]dScx+=r0p' <<< '153'
1

bash-4.1$ dc -e '[1pq]Sr?d0rdZSz[d10/r10%lz^rSh+Lhd0!=c]dScx+=r0p' <<< '1634'
1

bash-4.1$ dc -e '[1pq]Sr?d0rdZSz[d10/r10%lz^rSh+Lhd0!=c]dScx+=r0p' <<< '2013'
0

manatwork

Posted 2013-11-14T01:55:37.983

Reputation: 17 865

Never actually used dc, save for frantic typos in attempt to write cd – Stan Strum – 2018-01-05T01:54:16.427

8

R, 53 bytes

sum(scan(t=gsub("(.)","\\1 ",x<-scan()))^nchar(x))==x

The gsub regex inserts spaces in between characters, so that the scan function will be able to read the number into a vector of digits.

flodel

Posted 2013-11-14T01:55:37.983

Reputation: 2 345

+1 i would have never thought of doing that, it's brilliant. – plannapus – 2013-11-15T16:26:51.103

6

Kona, 18

...

{x=+/(0$'u)^#u:$x}

tmartin

Posted 2013-11-14T01:55:37.983

Reputation: 3 917

6

Powershell, 75 63 62 60 58

Edit: Updated per @Iszi's comment (note: this counts on $x not existing)

Edit: Added @Danko's changes.

[char[]]($x=$n=read-host)|%{$x-="$_*"*$n.length+1|iex};!$x

58 56 chars

If input is limited to 10 digits (includes all int32)

($x=$n=read-host)[0..9]|%{$x-="$_*"*$n.length+1|iex};!$x

Rynant

Posted 2013-11-14T01:55:37.983

Reputation: 2 353

I was wondering if someone was going to do PowerShell before I did. – Iszi – 2013-11-14T20:55:09.917

Save 12 characters by adding another variable $x and using += to do your summing instead of measure -sum then test $x-eq$n. – Iszi – 2013-11-14T21:03:08.960

@Iszi - Thanks for pointing that out. I updated the answer. – Rynant – 2013-11-14T21:21:11.583

For future reference, if measure -sum is ever actually necessary, you could get away with just measure -s. – Iszi – 2013-11-14T22:51:59.383

More tips for PowerShell you might want to check out. http://codegolf.stackexchange.com/q/191/9387 I'm going to have to go edit some of my other answers, now.

– Iszi – 2013-11-14T23:55:11.333

62 chars solution that doesn't count on $x not existing: $x=$n=read-host;$n-split''|%{$x-=[math]::pow($_,$n.length)};!$x You set $x=$n initially, subtract from$xin the loop, and then compare it to0` at the end. – Danko Durbić – 2013-11-15T08:53:57.590

161 chars: ($x=$n=read-host)-split''|%{$x-=[math]::pow($_,$n.length)};!$x – Danko Durbić – 2013-11-15T09:04:36.203

1@DankoDurbić, Nice! Type coercion often comes in handy with PoSh code golfing. I only get 62 though when I run '($x=$n=read-host)-split""|%{$x-=[math]::pow($_,$n.length)};!$x'.length – Rynant – 2013-11-15T15:06:47.650

1@Rynant Good point. I ran your length check in PowerShell and came up with 62 as well. When running a length check similarly against the actual script, it comes up 61. This is probably because of how PowerShell handles the '' which you replaced with ''. I took the original script into Excel to double-check with =LEN("($x=$n=read-host)-split''|%{$x-=[math]::pow($_,$n.length)};!$x") and got 62 also. Of course, we could always count it manually - but who really does that? – Iszi – 2013-11-15T15:22:33.993

Correction: "...how PowerShell handles the '' which you replaced (appropriately, for the purposes of counting characters) with ""." – Iszi – 2013-11-15T15:29:32.173

You can shorten [math]::pow with mutiplication. For example, [math]::pow(2,3) is "1*2*2*2"|iex, or generally [math]::pow($a,$b) is "1"+"*$a"*$b|iex, which is two characters shorter. With this little trick, I get [char[]]($x=$n=read-host)|%{$x-="1"+"*$_"*$n.length|iex};!$x which should be 60 characters, if I'm counting right. This doesn't quite work with -split'' because split returns empty strings at the beginning and the end (why?) "123"-split'' is actually "","1","2","3","". – Danko Durbić – 2013-11-15T15:43:52.590

@DankoDurbić I don't know why -split'' does that, but that's why my Keith Number Checker pipes it to ?{$_}. I used to use ?{$_-ne''} but Rynant pointed out that (for some reason I don't understand either) -ne'' is not needed. I like that, by sending [char[]] objects through iex, you're completely side-stepping the issue of object type - in fact, you're leveraging it to your advantage to build out the exponent equations! I'll have to remember that!

– Iszi – 2013-11-15T17:51:21.183

@DankoDurbić Thanks, updated again. @Iszi - ?{$_} works because the result of the ScriptBlock for the Where-Object CmdLet is coerced to a bool, and empty strings evaluate as False (see [bool]''). You have to be careful when filtering integers because 0 evaluates to False (try 0,1,2|?{$_} vs '0','1','2'|?{$_}) – Rynant – 2013-11-15T18:26:02.533

@Rynant Great information. So, I just have to keep in mind only to use filtering like that when working on numbers as strings, not integers, and I'm good? – Iszi – 2013-11-15T20:40:50.450

Just realized that you can replace the {$x-="1"+"*$_"*$n.length|iex} part with {$x-="$_*"*$n.length+1|iex} which saves another two characters. – Danko Durbić – 2013-11-15T22:08:16.733

Since PowerShell's default number type is int32, are your solutions really any different in limitations? – Iszi – 2013-12-08T13:09:17.593

5

Python 2.x - 51

Same concept as crazedgremlin's solution for Python 3.x:

s=input();print s==sum(int(c)**len(`s`)for c in`s`)

user1354557

Posted 2013-11-14T01:55:37.983

Reputation: 251

4

C - 97 93 characters

a,b;main(c){scanf("%d",&c);b=c;for(;c;c/=10)a+=pow(c%10,(int)log10(b)+1);printf("%d",a==b);}

With indentation:

a,b;
main(c) { 
  scanf("%d",&c);
  b=c;
  for(;c;c/=10)
    a+=pow(c%10,(int)log10(b)+1);
  printf("%d",a==b);
}

Josh

Posted 2013-11-14T01:55:37.983

Reputation: 2 783

Woah. You're reading the input into argc. – SIGSTACKFAULT – 2017-01-06T14:16:33.813

Also, shouldn't having to do -lm at compile-time count +1 byte? – SIGSTACKFAULT – 2017-01-06T14:21:25.513

@Blacksilver the -lm flag is not required for C89 compilers. – Josh – 2017-01-09T14:55:19.007

Aha. Learn a new thing every day. – SIGSTACKFAULT – 2017-01-09T14:59:41.127

2You don't have to define int for global variables. – Konrad Borowski – 2014-01-10T15:49:34.477

4

Delphi - 166

uses System.SysUtils,math;var i,r,l:integer;s:string;begin r:=0;readln(s);l:=length(s);for I:=1to l do r:=round(r+power(strtoint(s[i]),l));writeln(inttostr(r)=s);end.

With indent

uses System.SysUtils,math;
var
  i,r,l:integer;
  s:string;
begin
  r:=0;
  readln(s);
  l:=length(s);
  for I:=1to l do
    r:=round(r+power(strtoint(s[i]),l));
  writeln(inttostr(r)=s);
end.

Teun Pronk

Posted 2013-11-14T01:55:37.983

Reputation: 2 599

4

05AB1E, 7 bytes (Non-competing)

DSDgmOQ

Try it online!

-2 bytes thanks to @daHugLenny

Magic Octopus Urn

Posted 2013-11-14T01:55:37.983

Reputation: 19 422

3You can replace §1ô with S – acrolith – 2016-11-08T15:45:13.467

3

Japt, 14 9 7 bytes

¶ì_xpZÊ

Try it online


Explanation

Implicit input of integer U.

ì_

Convert U to an array of digits (ì), pass it through a function and convert back to an integer after.

xpZÊ

Reduce by addition (x), raising each element to the power (p) of the length (Ê) of the array in the process.

Check if the result is strictly equal to U.

Shaggy

Posted 2013-11-14T01:55:37.983

Reputation: 24 623

I think ¥U¬®n pUlÃx would work for 11 bytes ;) – Oliver – 2017-05-18T17:39:39.733

3

Haskell 2010 - 76 characters

main=do x<-getLine;print$(==x)$show$sum$map((^length x).(+(-48)).fromEnum)x

Nathan Baum

Posted 2013-11-14T01:55:37.983

Reputation: 51

1You shouldn't post the number of ms to run the code, but the number of chars you used. ;) – user unknown – 2013-11-15T04:02:02.107

3

Bash, 64 chars

for((a=$1;a>0;s+=(a%10)**${#1},a/=10));do :; done;echo $[s==$1]

a=$1;p=${#a};for((;a>0;a/=10));do s=$((s+(a%10)**p));done;echo $((s==$1))

user unknown

Posted 2013-11-14T01:55:37.983

Reputation: 4 210

1You are using variable p in a single place, so no need for it. You can move the initialization of variable a into the for to spare its separate ;: for((a=$1;a>0;a/=10));do s=$[s+(a%10)**${#1}];done;echo $[s==$1]. – manatwork – 2013-11-15T11:08:23.347

1By moving the evaluation into the for one more character can be shortened: for((a=$1;a>0;s+=(a%10)**${#1},a/=10));do :; done;echo $[s==$1]. – manatwork – 2013-11-15T11:16:45.583

Oh, curious! I tried something like that, but it didn't work. Curious what went wrong. – user unknown – 2013-11-16T01:53:57.900

3

Awk: 40 39 characters

{for(;i<NF;)s+=$(i+++1)**NF;$0=$0==s}1

Sample run:

bash-4.1$ awk -F '' '{for(;i<NF;)s+=$(i+++1)**NF;$0=$0==s}1' <<< '153'
1

bash-4.1$ awk -F '' '{for(;i<NF;)s+=$(i+++1)**NF;$0=$0==s}1' <<< '1634'
1

bash-4.1$ awk -F '' '{for(;i<NF;)s+=$(i+++1)**NF;$0=$0==s}1' <<< '2013'
0

manatwork

Posted 2013-11-14T01:55:37.983

Reputation: 17 865

3

JavaScript - 70 58 characters

for(i in a=b=prompt())b-=Math.pow(a[i],a.length)
alert(!b)

Note:

If you're testing this in your dev console on Stack Exchange, be aware that there are a number of non-standard properties added to String.prototype that will break this solution, such as String.prototype.formatUnicorn. Please be sure to test in a clean environment, such as on about:blank.

zzzzBov

Posted 2013-11-14T01:55:37.983

Reputation: 2 915

@koko, I've added a note to explain why you're receiving incorrect results. – zzzzBov – 2016-11-08T15:00:26.690

I count 70 characters there. – manatwork – 2013-11-15T16:10:42.587

@manatwork, whoops, forgot to count the newline. – zzzzBov – 2013-11-15T19:10:28.127

Great trick that decrementation! – manatwork – 2013-11-16T13:12:06.200

You can save some bytes by using the ** operator instead of Math.pow – Patrick Stephansen – 2018-01-29T11:07:35.100

2it always returns true for me, regardless of input – koko – 2014-07-08T09:27:17.667

3

Lua (101 chars)

Lua isn't known for being concise, but it was fun to try anyway.

for n in io.lines()do l,s=n:len(),0 for i=1,l do d=n:byte(i)s=s+(d-48)^l end print(s==tonumber(n))end

Improvements welcome.

criptych stands with Monica

Posted 2013-11-14T01:55:37.983

Reputation: 181

As it is not required that your program can handle and process a list of numbers, I would not use bytes to implement that functionality. Replacing the loop for n in io.lines()do [...]end with n=io.read() saves some bytes (TIO).

– Jonathan Frech – 2017-09-01T19:55:23.027

3

Java - 84 bytes

(a,l)->{int s=0;for(byte c:a.getBytes())s+=Math.pow(c-48,l);return a.equals(""+s);};

Non-lambda version: 101 bytes:

boolean n(String a,int l){int s=0;for(byte c:a.getBytes())s+=Math.pow(c-48,l);return a.equals(""+s);}

Called like this:

interface X {
    boolean n(String a, int l);
}

static X x = (a,l)->{int s=0;for(byte c:a.getBytes())s+=Math.pow(c-48,l);return a.equals(""+s);};

public static void main(String[] args) {
    System.out.println(n("153",3));
    System.out.println(n("1634",4));
    System.out.println(n("123",3));
    System.out.println(n("654",3));
}

Returns:

true
true
false
false

Hypino

Posted 2013-11-14T01:55:37.983

Reputation: 221

You can remove the parenthesis around the lambda arguments, a,l-> works exactly the same. – FlipTack – 2017-01-06T19:50:42.530

I know you've answer this almost a year ago, but you can golf two bytes: (a,l)-> can be a->l-> and byte can be int: a->l->{int s=0;for(int c:a.getBytes())s+=Math.pow(c-48,l);return a.equals(""+s);}

– Kevin Cruijssen – 2017-09-18T14:47:20.153

2

Jelly, 6 bytes (non-competing)

D*L$S=

Try it online!

D        Get the digits of the input
 *L$     Raise each element to power of its length
    S    Sum
     =   Equals input?

Lynn

Posted 2013-11-14T01:55:37.983

Reputation: 55 648

2

F# - 92 chars

let n=stdin.ReadLine()
n|>Seq.map(fun x->pown(int x-48)n.Length)|>Seq.sum=int n|>printf"%b"

Smetad Anarkist

Posted 2013-11-14T01:55:37.983

Reputation: 363

2

Common Lisp - 116 102 characters

(defun f(m)(labels((l(n)(if(> n 0)(+(expt(mod n 10)(ceiling(log m 10)))(l(floor n 10)))0)))(= m(l m))))

Formatted:

(defun f(m)
  (labels((l(n)
            (if(> n 0)
               (+(expt(mod n 10)(ceiling(log m 10)))
                 (l(floor n 10)))
               0)))
    (=(l m)m)))

Paul Richter

Posted 2013-11-14T01:55:37.983

Reputation: 770

2

Smalltalk - 102 99 characters

[:n|a:=n asString collect:[:e|e digitValue]as:Array.^n=(a collect:[:each|each raisedTo:a size])sum]

At the Workspace, send value: with the number, and Print It.

Paul Richter

Posted 2013-11-14T01:55:37.983

Reputation: 770

2

APL (Dyalog Unicode), 8 bytesSBCS

Tacit prefix function taking the input as a string.

⍎≡1⊥⍎¨*≢

Try it online!

 is the evaluated argument

 identical to

1⊥ the sum (lit. convert from base-1) of

⍎¨ the evaluated characters (i.e the digits)

* raised to the power of

 the tally of characters (i.e. digits)

Adám

Posted 2013-11-14T01:55:37.983

Reputation: 37 779

2

C#, 117

using System.Linq;class A{int Main(string[] a){return a[0].Select(c=>c-'0'^a[0].Length).Sum()==int.Parse(a[0])?1:0;}}

It'sNotALie.

Posted 2013-11-14T01:55:37.983

Reputation: 209

2

Retina, 118 bytes

Byte count assumes ISO 8859-1 encoding.

.*
$0 $0¶$0
(?<=^\d*)\d
x
(?=.*$)
¶
0¶

\d+
$*
¶(1+)
¶$1 $1
{`^x ?

}s`(?<=x.*)1(?=1* (1+))
$1
 1*

1¶1
11
^(1*)¶+\1\b

Try it online


Explanation

.*                          # Copy number 3 times. For Length, Unary, and Digits
$0 $0¶$0
(?<=^\d*)\d                 # Convert first copy to x's (Length)
x
(?=.*$)                     # Split up digits of last copy, each on their own line
¶
0¶                          # Remove zeros, because they leave blank lines

\d+                         # Convert to unary
$*
¶(1+)                       # Duplicate each separated digit
¶$1 $1
{`^x ?                      # While x's exist, remove an x ...

}s`(?<=x.*)1(?=1* (1+))     #     and multiply each value by the digit (nth power)
$1
 1*                         # Remove original digits

1¶1                         # Remove lines between digits
11
^(1*)¶+\1\b                 # Match if values are equal

mbomb007

Posted 2013-11-14T01:55:37.983

Reputation: 21 944

2

Haskell, 68 66 bytes

d 0=[]
d n=mod n 10:d(div n 10)
sum.(\a->map(^length a)a).d>>=(==)

Usage:

*Main> sum.(\a->map(^length a)a).d>>=(==) $ 1634
True

Angs

Posted 2013-11-14T01:55:37.983

Reputation: 4 825

1

Clojure, 85 bytes

#(= n(int(reduce +(vec(map#(Math/pow(Character/digit % 10)(count(str n)))(str n))))))

Usage is like so:

(#(...) {number})

Ungolfed (with commentary):

(defn narcissistic [n]
  ; The function is altered a bit, to improve readability.
  ; The double arrow means that a result of a function will get "chained"
  ; onto the next function as the last argument:
  ; (->> 1 (* 2) (+ 3)) -> (->> (* 2 1) (+ 3)) -> (+ 3 (* 2 1))
  (->> n
    ; Converts it to a string, for the next function
    ; 153 -> "153"
    str
    ; Converts the string to an array of characters,
    ; which is then raised to the powers equal to the length of the number:
    ; 153 -> (1.0 125.0 27.0)
    (map (#(Math/pow (Character/digit % 10) (count (str n)))))
    ; Converts the array to a vector (reducing only works with vectors)
    ; (1.0 125.0 27.0) -> [1.0 125.0 27.0]
    vec
    ; Reduces the vector by adding them
    ; [1.0 125.0 27.0] -> 153.0
    (reduce +)
    ; Turns that into an integer
    ; 153.0 -> 153
    int
    ; Checks if that's equal to the original n
    ; 153 = 153 -> true
    (= n)))

clismique

Posted 2013-11-14T01:55:37.983

Reputation: 6 600

1

Befunge 98, 58 bytes

1-00p&:a\v
 00g1+00p>:a%\a/:!kv
 \:9`kv00gk:00gk*+>
@.!-$<

Try it Online!

I'm sure this can be golfed further. I will take another look at it and add an explanation later...

MildlyMilquetoast

Posted 2013-11-14T01:55:37.983

Reputation: 2 907

1

Add++, 16 bytes

L,BDdbLdXBcB`sA=

Try it online!

caird coinheringaahing

Posted 2013-11-14T01:55:37.983

Reputation: 13 702

1

K (ngn/k), 22 bytes

{x~+/*/'(#:r)#'r:10\x}

Try it online!

Thaufeki

Posted 2013-11-14T01:55:37.983

Reputation: 421

there's no need for a : after a monadic verb, #:r -> #r – ngn – 2018-11-05T17:53:06.773

1

Brachylog, 10 bytes

lg;?↔z^ᵐ+?

Try it online!

The predicate succeeds if the input is an Armstrong number and fails if it is not. If run as a full program, success prints true. and failure prints false.

lg;?↔z     A list of pairs [a digit of input, the length of input].
      ^ᵐ   A list of numbers where each is a digit of the input raised to the power of its length.
        +  The sum of those numbers.
         ? Attempt to unify that sum with the input.

Unrelated String

Posted 2013-11-14T01:55:37.983

Reputation: 5 300

Originally, this was nine bytes, but I realized that if I gave it a number more than nine digits long it would stop acting correctly, as previously I hadn't put g in there and it worked by virtue of single-digit lengths being length-1 sequences of themselves. – Unrelated String – 2019-03-01T06:30:30.833

1

Not the sortest but my take.

Python 2.7: 59 60 chars

a=input();(0,1)[sum(int(i)**len(str(a))for i in str(a))==a]

Eduard Florinescu

Posted 2013-11-14T01:55:37.983

Reputation: 1 863

It's supposed to output true or false (also needs to take input). – Timtech – 2014-01-10T11:46:17.533

@Timtech or 1 and 0 – Eduard Florinescu – 2014-01-10T14:05:59.483

@EduardFlorinescu Still needs to take input. – Iszi – 2014-01-10T14:12:49.893

@lszi now should work ;) – Eduard Florinescu – 2014-01-10T15:13:17.303

Yes, it seems to work now. – Timtech – 2014-01-10T15:23:51.103

2For converting boolean value to integer int(BoolExpr) is shorter than (0,1)[BoolExpr]. +(BoolExpr) even shorter. – AMK – 2014-01-11T18:24:53.287

1

Pyth, 13 characters

JwqvJsm^vdlJJ

Explanation:

Jw                J=input()
       ^vdlJ      eval(d)^len(J)
      m^vdlJJ     map each character in J to eval(d)^len(J)
  qvJsm^vdlJJ     print(eval(J)==sum(map each character in J to eval(d)^len(J)))

isaacg

Posted 2013-11-14T01:55:37.983

Reputation: 39 268

1

Python, 90 Bytes

a,z=input(),[]
for x in list(a):z.append(int(x)**len(a))
print(1 if sum(z)==int(a) else 0)

Mitchell Humphrey

Posted 2013-11-14T01:55:37.983

Reputation: 348

1

C, 252 220 225 111 bytes

int f(char *a){for(int i=0;i<strlen(a);i++){r+=((int)a[i]);for(int j=0;j<strlen(a);j++)r*=r;}return r==(int)a;}

Returns 0 if false and 1 if true. Thanks to @DrMcMoylex for saving many bytes and explaining stuff.

Aryaman

Posted 2013-11-14T01:55:37.983

Reputation: 161

Welcome to the site! Some tips for you: 1) You have a lot of unnecessary whitespace. You could remove most of the newlines and spaces/indentation and it would still run fine. 2) A function is allowed, so you could return '1' or '0' instead of printing it. That would save a lot of bytes. 3) Since you're only doing one thing in each 'for' loop, you could join the inner code with the loop itself. For example: for(int i=0;i<strlen(a);r+=a[i++]) – James – 2016-11-08T17:56:35.973

@DrMcMoylex How would you know the output if I used return? There's nothing printed in the terminal... – Aryaman – 2016-11-08T18:48:08.630

You could write a small wrapper to print the return value of the function – James – 2016-11-08T18:51:37.470

@DrMcMoylex Using printf instead of making a new function uses less bytes, I believe. Thanks for the welcome, btw! – Aryaman – 2016-11-08T19:03:18.377

1No that's not what I meant. I meant you don't need to print anything. Returning is a valid form of output. You could print the return value for testing, but your submission can just be a function. Then you won't need to parse input or print the output. For example int f(char *a){for(int i=0;i<strlen(a);i++){r+=((int)a[i]);for(int j=0;j<strlen(a);j++)r*=r;}return r==(int)a;} – James – 2016-11-09T19:15:39.870

1

JavaScript, 56 characters

n=prompt();n.split('').reduce((a,i)=>a+i**n.length,0)==n

This makes use of the exponentiation operator, so you have to be running a modern browser for this to work.

Jrop

Posted 2013-11-14T01:55:37.983

Reputation: 121

1

Perl, 27 +3 = 30 bytes

Run with -F. Older versions of Perl might require you to run with -nF instead, if -F does not imply -n.

grep$;+=$_**$#F,@F;say$_==$

Prints 1 if narcissistic, prints nothing otherwise.

(thanks to @Dada for byte-count correction, and for -2 bytes)

Gabriel Benamy

Posted 2013-11-14T01:55:37.983

Reputation: 2 827

grep$;+=$_**$#F,@F;say$_==$ to save two bytes ($; instead of $a, and grep...,@F instead of grep{...}@F). However, note that -F counts as 3 bytes (-, F and a space). – Dada – 2016-11-11T18:27:07.487

0

Pyke, 8 bytes (noncompeting)

YQ`lL^sq

Try it here!

 Q`l     -   len(str(input))
    L^   -  map(^ ** V)
Y        -   digits(input)
      s  -  sum(^)
       q - ^ == input

Blue

Posted 2013-11-14T01:55:37.983

Reputation: 26 661

0

JavaScript (ES6), 56 bytes

eval(`${n=prompt()}0`.split``.join(`**${n.length}+`))==n

George Reith

Posted 2013-11-14T01:55:37.983

Reputation: 2 424

0

Pushy, 9 bytes

Note that this answer is non-competing as Pushy postdates the challenge. However, I thought I'd post it because it's interestingly short for a simple stack-based language:

VsLKeS^=#

Try it online!

It works like this (how the two stacks would look for the example input is shown on the right):

    \ Implicit input, for example 1634.  [1634], []
V   \ Copy into second stack.            [1634], [1634]
s   \ Split into individual digits       [1,6,3,4], [1634]
L   \ Push stack length                  [1,6,3,4,4], [1634]
Ke  \ Raise all to this power            [1,1296,81,256], [1634]
S   \ Take sum                           [..., 1634], [1634]
^=  \ Check equality with initial input  [..., True], []
#   \ Output this boolean (as 0/1)     

FlipTack

Posted 2013-11-14T01:55:37.983

Reputation: 13 242

0

Perl 6, 30 bytes

{$_==sum .comb.map(* **.comb)}

Pretty straightforward. The chars method would be more typically used to get the number of characters in the input string, but comb returns those characters as a list, which evaluates to the number of characters in numeric context, and saves us a byte.

Sean

Posted 2013-11-14T01:55:37.983

Reputation: 4 136

25 bytes – Jo King – 2018-11-07T05:42:06.133

0

JavaScript (ES7), 43 38 bytes

Takes input as a string.

n=>n==eval([...n,0].join`**n.length+`)

Try It

f=
n=>n==eval([...n,0].join`**n.length+`)
o.innerText=f(i.value="153")
oninput=_=>o.innerText=f(i.value)
<input id=i type=number><pre id=o>

Shaggy

Posted 2013-11-14T01:55:37.983

Reputation: 24 623

0

Bash, 54 bytes

echo $[ `printf "+%c**${#1}" $(fold -w1<<<$1)` == $1 ]

Try it online!

Takes input as parameter, outputs 1 if is narcissist, 0 if not.

fold prints each digit one per line, printf adds +<digit>**<length> forming the arithmetic expression which is evaluated and compared to the original input.

marcosm

Posted 2013-11-14T01:55:37.983

Reputation: 986

0

Python 2, 44 bytes

I think this is the shortest you can get for Python. Uses a lambda rather than a full program.

lambda s:sum(int(x)**len(`s`)for x in`s`)==s

Try it online!

Based off @danmcardle's answer.

Original answer, 51 bytes

lambda s:sum(map(lambda x:int(x)**len(`s`),`s`))==s

Try it online!

caird coinheringaahing

Posted 2013-11-14T01:55:37.983

Reputation: 13 702

You could use strings as input and save a byte.

– Jonathan Frech – 2017-09-19T06:49:01.580

0

Pyth (non-competing), 10 bytes

qsm^sdl`Q`

Verify the test cases.

Mr. Xcoder

Posted 2013-11-14T01:55:37.983

Reputation: 39 774

0

Perl 5, 24 bytes

21 bytes of code + 3 for -pF flags

for$i(@F){$_-=$i**@F}

Try it online!

Xcali

Posted 2013-11-14T01:55:37.983

Reputation: 7 671

0

Swift 3.2: 107 characters

Of course Swift is absolutely not a quick language but I thought I would try:

func n(s:String){let c=s.utf8.map{Double($0)-48};print(c.reduce(0){$0+pow($1,Double(c.count))}==Double(s))}

Eric

Posted 2013-11-14T01:55:37.983

Reputation: 101

0

JavaScript 46 bytes

F=n=>![...n].reduce((x,c)=>x-(+c)**n.length,n)

console.log(F("153") == true)
console.log(F("370") == true)
console.log(F("371") == true)
console.log(F("152") == false)
console.log(F("150") == false)

DanielIndie

Posted 2013-11-14T01:55:37.983

Reputation: 1 220

Is it necessary to convert c into number? – l4m2 – 2018-01-05T04:14:19.010

0

Pyt, 11 bytes

ĐĐḶ⌊⁺⇹ą⇹^Ʃ=

Explanation:

                      Implicit input
ĐĐ                    Duplicate the input twice
   Ḷ⌊⁺                Get number of digits in the input
      ⇹ą              Convert input to array of digits
        ⇹^Ʃ           sum the digits raised to the power of the number of digits
           =          equals input?

Try it online!

mudkip201

Posted 2013-11-14T01:55:37.983

Reputation: 833

0

JavaScript 7, 41 Bytes

s=>[...s].map(x=>N+=x**s.length,N=0)|N==s

l4m2

Posted 2013-11-14T01:55:37.983

Reputation: 5 985

0

CJam, 12 bytes

{_Ab_,f#:+=}

Try it online!

Explanation:

{          }   anonymous block, input: 1634
   b           get digits in base
  A              10: [1 6 3 4]
     ,         take the length: 4
       #       and raise
      f          each element
    _              of the list of digits
               to that power: [1 1296 81 256]
        :      fold over
         +       addition: 1634
          =    and compare
 _               to the original: 1 (true)

Esolanging Fruit

Posted 2013-11-14T01:55:37.983

Reputation: 13 542

0

Kotlin, 60 bytes

map{Math.pow(it-'0'+0.0,length+0.0)}.sum()==this.toInt()+0.0

Beautified

map {
    Math.pow(it - '0' + 0.0, length + 0.0)
}.sum() == this.toInt() + 0.0

Test

fun String.f() =
map{Math.pow(it-'0'+0.0,length+0.0)}.sum()==this.toInt()+0.0

fun main(args: Array<String>) {
    (0..1000).filter { it.toString().f() }.forEach { println(it) }
}

TIO

TryItOnline

jrtapsell

Posted 2013-11-14T01:55:37.983

Reputation: 915

0

Javascript (ES6) 46 bytes - Not competing

n=>(s=[...''+n]).forEach(v=>n-=v**s.length)|!n

Explanation:

n=>
(s=[...''+n])        // Convert input to array of chars and assign to s
  .forEach(v=>       // Loop over s (returns undefined)
    n-=v**s.length)  // reduce input by char^length
  |                  // undefined is falsy, so we OR
  !n                 // OR with negated input 
                     // returns 1 if 0, 0 otherwise

Brian H.

Posted 2013-11-14T01:55:37.983

Reputation: 513

0

R - 216

Here is a long-ish R attempt:

fnNar = function(x = NULL) {
  if(is.null(x)) x = readline('Enter a positive integer: ')
  digits = as.double(unlist(strsplit(as.character(x), split = '')))
  exponent = length(digits)
  return(x == sum(digits ^ exponent))
}

# test the function
fnNar()

# test the function
fnNar(153)
fnNar(1634)
fnNar(101)

tchakravarty

Posted 2013-11-14T01:55:37.983

Reputation: 119

2

This is a [tag:code-golf] challenge, so please include your code's size in the post's heading. For now I count 216 characters, but I am sure you could reduce it by applying some tips from Tips for golfing in R? and Tips for golfing in <all languages>.

– manatwork – 2013-12-08T12:45:26.570

0

Pari/GP, 35 bytes

n->n==vecsum([d^#s|d<-s=digits(n)])

Try it online!

alephalpha

Posted 2013-11-14T01:55:37.983

Reputation: 23 988

0

Ly, 51 bytes

ns>lS0sp11[ppl:Isp>l<ysp>l<sp>,^<l`sy,=!]>&+s<<l=fp

Try it online!

LyricLy

Posted 2013-11-14T01:55:37.983

Reputation: 3 313

0

Tcl, 77 bytes

proc N n {expr [join [lmap d [split $n ""] {expr $d**[string le $n]}] +]==$n}

Try it online!

sergiol

Posted 2013-11-14T01:55:37.983

Reputation: 3 055

0

Python 2.7 - 57 chars

i=`input()`
print`sum(map(lambda x:int(x)**len(i),i))`==i

There is a shorter Python answer, but I might as well toss in my contribution.

i=`input()`

i is set to input() surrounded by backticks (which is surprisingly hard to type through SE's markdown interpreter). Surrounding x with backticks is equivalent to str(x). [backtick]input()[backtick] saves two characters over raw_input() in any case where we can assume the input is an int, which we're allowed to do:

Error checking for text strings or other invalid inputs is not required.

Once i is a string containing the user's input, the next line is run. I'll explain this one from the inside out:

map(lambda x:int(x)**len(i),i)

map is a function in Python that takes a function and an iterable as arguments and returns a list of each item in the iterable after having the function applied to it. Here I'm defining an anonymous function lambda x which converts x to a string and raises it to the power of the length of i. This map will return a list of each character in the string i raised to the correct power, and even nicely converts it to an int for us.

`sum(map(lambda x:int(x)**len(i),i))`

Here I take the sum of each value in the list returned from the map. If this sum is equal to the original input, we have a narcissistic number. To check this, we either have to convert this sum to a string or the input to an int. int() is two more characters than two backticks, so we convert this to a string the same way we did with the input.

print`sum(map(lambda x:int(x)**len(i),i))`==i

Compare it to i and print the result, and we're done.

undergroundmonorail

Posted 2013-11-14T01:55:37.983

Reputation: 5 897

0

Racket 115 bytes

(let*((l(number->string n))(g(string-length l))(m(for/sum((i l))(expt(string->number(string i))g))))(if(= m n)1 0))

Ungolfed:

(define (f n)
  (let* ((l (number->string n))
         (g (string-length l))
         (m (for/sum ((i l))
              (expt (string->number(string i)) g))))
    (if (= m n) 1 0)))

Testing:

(f 153)
(f 1634)
(f 123)
(f 654)

Output:

1
1
0
0

rnso

Posted 2013-11-14T01:55:37.983

Reputation: 1 635

0

Jelly, 7 bytes (non-competing)

D*DL$S⁼

Try it online!

Or alternatively (uses 2 chains):

Dµ*LS⁼Ḍ

Explanation of the first code:

 D* DL$S⁼  Main link (monadic). Arguments: z
⁸          (implicit) z
 D         List of digits of z
   ⁸       (implicit) z
    D      List of digits of z
     L     Length of z
      $    Last two links as a monad
  *        Exponentiation with base x and exponent y
       S   Sum of z
         ⁸ (implicit) z
        ⁼  Check if x equals y

Erik the Outgolfer

Posted 2013-11-14T01:55:37.983

Reputation: 38 134

0

C#, 103 Bytes

Golfed:

bool N(int n){double a=0;foreach(var d in n+""){a+=Math.Pow(int.Parse(d+""),n+"".Length);}return a==n;}

Ungolfed:

public bool N(int n)
{
  double a = 0;

  foreach (var digit in n.ToString())
  {
    a += Math.Pow(int.Parse(digit + ""), n.ToString().Length);
  }

  return a == n;
}

Testing:

Console.WriteLine(new NarcissisticNumber().N(153));
True

Console.WriteLine(new NarcissisticNumber().N(1634));
True

Pete Arden

Posted 2013-11-14T01:55:37.983

Reputation: 1 151

0

Clojure, 110 bytes

(fn[](let[s(read-line)p #(Integer/parseInt(str %))](=(p s)(reduce + 0(map #(int(Math/pow(p %)(count s)))s)))))

Reads in the user input, maps over the digits, raising each to a power equal to the number of digits in the number, then checks that the sum of the digits equals the number itself.

Ungolfed (and neatened up):

(defn narcissistic? []
  (let [n-str (read-line)
        parse #(Integer/parseInt (str %))
        pow #(int (Math/pow % (count n-str)))
        powd-digits (map #(pow (parse %)) n-str)]
    (= (parse n-str) (reduce + 0 powd-digits))))

Carcigenicate

Posted 2013-11-14T01:55:37.983

Reputation: 3 295

0

JavaScript ES6, 50 bytes

v=>[...s=v+""].map(x=>v-=Math.pow(x,s.length))&&!v

Convert the number to a string and iterate through the digits, subtract the power computation from the original number use the ! operator to invert the logic so that a 0 result returns true and non-zero returns false.

Grax32

Posted 2013-11-14T01:55:37.983

Reputation: 1 282

0

k, 24 bytes

{x=+/*/(#$x)#,"I"$'$x}

Paul Kerrigan

Posted 2013-11-14T01:55:37.983

Reputation: 189

0

R, 173 Bytes

a=readline()
b=as.numeric(strsplit(as.character(a),"")[[1]])
x=(b)^length(b)
if(sum(x)==as.numeric(paste(b,sep="",collapse=""))){
   print("true")
} else{
  print("false")
}

brendanjhowell

Posted 2013-11-14T01:55:37.983

Reputation: 1

0

Factor, 90 bytes

[ read [ length ] [ >array [ 1string ] map [ 10 base> ] map ] bi [ swap ^ ] with map sum ]

More readable and explained:

[ 
    read                                  ! input 
    [ length ]                            ! a function which gets the length 
    [ >array [ 1string ] map [ 10 base> ] map ] ! another which turns a number into an array
    bi                                    ! apply both to the string input
    [ swap ^ ] with map sum               ! raise each digit to the length power and sum
]       

cat

Posted 2013-11-14T01:55:37.983

Reputation: 4 989