Home Forums HCL Reviews Tutorials Articles Register Search Today's Posts Mark Forums Read
 LinuxQuestions.org Printing Armstrong numbers from 1 to 500. (C Programming)
 Programming This forum is for all programming questions. The question does not have to be directly related to Linux and any language is fair game.

Notices

 07-23-2006, 11:05 AM #1 duffmckagan Senior Member   Registered: Feb 2005 Distribution: Cent OS 6.4 Posts: 1,163 Rep: Printing Armstrong numbers from 1 to 500. (C Programming) Code: ```/* Write a program to print out all Armstrong numbers between 1 and 500. If sum of cubes of each digit of the number is equal to the number itself, then the number is called an Armstrong number. For example, 153 = (1*1*1) + (5*5*5) + (3*3*3) */ #include main() { int number, temp, digit1, digit2, digit3; printf("Printing all Armstrong numbers between 1 and 500:\n\n"); number = 001; while (number <= 500) { digit1 = number%10; digit2 = (number%100) - ((number/100)*10); digit3 = number%1000; temp = (digit1*digit1*digit1) + (digit2*digit2*digit2) + (digit3*digit3*digit3); if (temp == number) { printf("\nAmstrong Number:%d", temp); } number++; } }``` Whats wrong with the program? It does not give a single number in the output!
 07-23-2006, 11:25 AM #2 michaelk Moderator   Registered: Aug 2002 Posts: 16,347 Rep: Per the rules: Do not expect LQ members to do your homework - you will learn much more by doing it yourself. However, providing hints is acceptable. Have you verified that digit1, digit2 and digit3 equations actually produce the correct values of your number?
 07-23-2006, 11:27 AM #3 duffmckagan Senior Member   Registered: Feb 2005 Distribution: Cent OS 6.4 Posts: 1,163 Original Poster Rep: Hey..i was not expecting you to do my homework!! I worked all the way upto this step..and still the program is not working..so I asked for help! well.I changed the Digit Extraction scheme and it worked Changed it to this: Code: ```digit1 = number - ((number / 10) * 10); digit2 = (number / 10) - ((number / 100) * 10); digit3 = (number / 100) - ((number / 1000) * 10);``` 1 members found this post helpful.
 07-23-2006, 11:38 AM #4 michaelk Moderator   Registered: Aug 2002 Posts: 16,347 Rep: Well done.
 07-23-2006, 01:32 PM #5 graemef Senior Member   Registered: Nov 2005 Location: Hanoi Distribution: Fedora 13, Ubuntu 10.04 Posts: 2,379 Rep: Just to comment on what you have done, Whilst your second approach is correct, it is a little ungainly, the first approach to get the digits actually had some merit. With a little more thought, you can make that code much cleaner. And for the moment I'll leave it there as a poser...
 06-11-2017, 01:22 AM #6 Lalit Yogi LQ Newbie   Registered: Jun 2017 Posts: 1 Rep: slightly alternate solution- #include void main() { int number,temp,digit1,digit2,digit3; for(number=001;number<=500;number++) { digit1 = number - ((number/10)*10); digit2 = (number - ((number/100)*100))/10; digit3 = number/100; temp = (digit1*digit1*digit1) + (digit2*digit2*digit2) + (digit3*digit3*digit3); if(temp==number) printf("\nArmstrong number: %d",temp); } } Here in my code, digit2 and digit3 values are a little different- digit1 = number - {(number/10)*10} digit2 = {number - ((number/100)*100)}/10 digit3 = number / 100
 06-11-2017, 02:42 AM #7 astrogeek Moderator   Registered: Oct 2008 Distribution: Slackware [64]-X.{0|1|2|37|-current} ::12<=X<=14, FreeBSD_10{.0|.1|.2} Posts: 4,506 Blog Entries: 6 Rep: Welcome to LQ! You have posted to an 11 year dead thread, best to leave them at rest! Please start your own threads for your own questions. See the LQ posting guidelines foru guidance in posting your questions as well. And when you post code, please place your code snippets inside [CODE]...[/CODE] tags for better readability. You may type those yourself or click the "#" button in the edit controls. 1 members found this post helpful.
 06-11-2017, 11:10 AM #8 GazL Senior Member   Registered: May 2008 Posts: 4,483 Blog Entries: 7 Rep: I'm glad he did, I enjoyed having a go at that one. BTW, watch out for those leading zeros! Code: `for(number=001;number<=500;number++)` It doesn't matter in this case, but leading zeros signify octal! Last edited by GazL; 06-11-2017 at 11:31 AM. 2 members found this post helpful.
06-11-2017, 04:56 PM   #9
danielbmartin
Senior Member

Registered: Apr 2010
Location: Apex, NC, USA
Distribution: Mint 17.3
Posts: 1,586

Rep:
Quote:
 Originally Posted by GazL I'm glad he did, I enjoyed having a go at that one.
Me too. Just for fun I wrote a non-C solution.
This code ...
Code:
```seq -w 500  \
|awk -F "" '{if (\$1^3+\$2^3+\$3^3==\$0) print}'```
... produced this result ...
Code:
```001
153
370
371
407```
Daniel B. Martin

3 members found this post helpful.
 06-12-2017, 11:13 AM #10 danielbmartin Senior Member   Registered: Apr 2010 Location: Apex, NC, USA Distribution: Mint 17.3 Posts: 1,586 Rep: Execution time is always of interest. The original problem statement (in post #1) is ... Code: ```Write a program to print out all Armstrong numbers between 1 and 500. If sum of cubes of each digit of the number is equal to the number itself, then the number is called an Armstrong number. For example, 153 = (1*1*1) + (5*5*5) + (3*3*3)``` Post #9 offered this concise non-C solution ... Code: ```echo "Method #1 of LQ Member danielbmartin." seq -w 500 \ |awk -F "" '{if (\$1^3+\$2^3+\$3^3==\$0) print}' >\$OutFile``` Consider a means to reduce execution time. Since the largest number must be less than 501, each of the individual terms \$1^3, \$2^3, and \$3^3 must be less than 501. The command seq -w 500 creates a stream of lines in the form Code: ```001 002 003 ... 498 499 500``` 8^3=512 and 9^3=729, so the stream may be "pruned" to eliminate all lines which contain an 8 or a 9, in this manner. Code: ```echo "Method #2 of LQ Member danielbmartin." seq -w 500 \ |egrep -v '[89]' \ |awk -F "" '{if (\$1^3+\$2^3+\$3^3==\$0) print}' >\$OutFile``` Pruning reduces the stream from 500 to 320 lines which leaves less work for the awk to do. This might seem like an improvement but it isn't, as shown below. Now, another surprise. A solution which uses only awk looks verbose and clumsy but turned out to be the fastest of the three. Code: ```echo "Method #3 of LQ Member danielbmartin." awk 'BEGIN{for (j=1;j<=500;j++) {k="00"j; a=substr(k,length(k)-2,3); # a = j with leading zeros h=substr(a,1,1); # h = hundreds t=substr(a,2,1); # t = tens u=substr(a,3,1); # u = units if (h^3+t^3+u^3==j) print a}}' >\$OutFile``` A measurement of each solution executed 1000 times produced this result ... Code: ```Method #1 of LQ Member danielbmartin, repeated 1000 times. real 0m2.356s user 0m0.060s sys 0m0.160s Method #2 of LQ Member danielbmartin, repeated 1000 times. real 0m2.649s user 0m0.064s sys 0m0.260s Method #3 of LQ Member danielbmartin, repeated 1000 times. real 0m1.779s user 0m0.060s sys 0m0.088s``` Perhaps the awk-savvy reader will know a better way to produce the three-digit lines 001,002, ... etc. Daniel B. Martin Last edited by danielbmartin; 06-12-2017 at 11:23 AM. Reason: Cosmetic improvement
 06-12-2017, 12:05 PM #11 KenJackson Member   Registered: Jul 2006 Location: Maryland, USA Distribution: Fedora, PCLinuxOS Posts: 666 Rep: Yeah, this is fun. Didn't time it. Code: ```awk 'BEGIN{for (h=0;h<8;h++) for (t=0;t<8;t++) for (u=0;u<8;u++) if ((h||t||u) && (h^3+t^3+u^3==h*100+t*10+u)) print h t u}'``` 1 members found this post helpful.
06-12-2017, 12:24 PM   #12
ntubski
Senior Member

Registered: Nov 2005
Distribution: Debian, Arch
Posts: 3,240

Rep:
Quote:
 Originally Posted by danielbmartin Perhaps the awk-savvy reader will know a better way to produce the three-digit lines 001,002, ... etc.
"Better" might be subjective, but some shorter ways are:

Code:
```BEGIN{for (j=1;j<=500;j++) {
h=int(j/100);     # h = hundreds
t=int(j/10) % 10; # t = tens
u=j % 10;         # u = units
if (h^3+t^3+u^3==j) print j}}```
Code:
```BEGIN{for (j=1;j<=500;j++) {
split(sprintf("%03d", j), digits, "");
if (digits[1]^3+digits[2]^3+digits[3]^3==j) print j}}```

1 members found this post helpful.
 06-12-2017, 03:48 PM #13 danielbmartin Senior Member   Registered: Apr 2010 Location: Apex, NC, USA Distribution: Mint 17.3 Posts: 1,586 Rep: Timings ... Code: ```Method #1 of LQ Member danielbmartin, repeated 1000 times. real 0m2.388s user 0m0.040s sys 0m0.184s Method #2 of LQ Member danielbmartin, repeated 1000 times. real 0m2.709s user 0m0.084s sys 0m0.232s Method #3 of LQ Member danielbmartin, repeated 1000 times. real 0m1.803s user 0m0.056s sys 0m0.096s Method #1 of LQ Member KenJackson, repeated 1000 times. real 0m1.418s user 0m0.048s sys 0m0.096s Method #1 of LQ Senior Member ntubski, repeated 1000 times. real 0m1.388s user 0m0.056s sys 0m0.096s Method #2 of LQ Senior Member ntubski, repeated 1000 times. real 0m2.437s user 0m0.052s sys 0m0.104s``` Nice ideas from everyone. Thank you! Daniel B. Martin
 06-12-2017, 03:59 PM #14 Laserbeak Member   Registered: Jan 2017 Location: Manhattan, NYC NY Distribution: Mac OS X, iOS, Solaris Posts: 508 Rep: There's two basic approaches -- try to calculate every Armstrong number between 1 and 500 or check every number between 1 and 500 to see if it's an Armstrong number. I assume this has already been made clear. Which is faster would need testing.
06-12-2017, 04:36 PM   #15
danielbmartin
Senior Member

Registered: Apr 2010
Location: Apex, NC, USA
Distribution: Mint 17.3
Posts: 1,586

Rep:
Quote:
 Originally Posted by Laserbeak There's two basic approaches -- try to calculate every Armstrong number between 1 and 500 or check every number between 1 and 500 to see if it's an Armstrong number. I assume this has already been made clear. Which is faster would need testing.
calculate every Armstrong number between 1 and 500
... this requires an algorithm. Do you know one?

check every number between 1 and 500 to see if it's an Armstrong number
... this is exhaustive enumeration and is the basis of all solutions posted so far. Granted, avoiding 8s and 9s is a small shortcut but all the posted solutions fall into the Brute Force category.

Daniel B. Martin

 Posting Rules You may not post new threads You may not post replies You may not post attachments You may not edit your posts BB code is On Smilies are On [IMG] code is Off HTML code is Off Forum Rules

 Similar Threads Thread Thread Starter Forum Replies Last Post bauer172uw Programming 3 04-14-2006 12:10 AM Gigantor Programming 8 12-05-2005 11:32 PM mrobertson Programming 1 06-28-2005 09:19 AM vijeesh_ep Programming 18 09-08-2004 12:59 PM fisheromen1031 Programming 1 07-27-2004 03:19 PM

LinuxQuestions.org

All times are GMT -5. The time now is 12:27 PM.

 Contact Us - Advertising Info - Rules - LQ Merchandise - Donations - Contributing Member - LQ Sitemap -