This week's book giveaway is in the Android forum. We're giving away four copies of Head First Android and have Dawn & David Griffiths on-line! See this thread for details.

public class Perfect_Num_Gen
{
public static void main(String [] args)
{
int calc = 0; int rem = 0;
for(int i = 1; i < 500; i++)
{
for(int j = 1; j < i; j++)
{
rem = i % j;
if(rem == 0)
calc = calc + i;
}
if(calc == i)
{
System.out.println("This number " + i + " is a perfect number.");
}
calc = 0;
}
}
}

This is the code I've written to generate a perfect number within the given range but this code is giving me wrong outputs. Please correct me if anything is wrong in my code! Thank You for helping in advance!

If by "perfect" you mean "prime," this seems to be working. What output are you getting that you don't like? (There are lots of other ways to do this, too, and some might be easier for you to put your faith in.)

For easier reference, I have reformatted your code with line numbers, using the perfect Allman/BSD indentation style:

One small point: Most Java programmers' class names do not use punctuation. "PerfectNumGen" would be the more common choice, I think.

Anyway, hoping I haven't scared him off... Ranajoy, your problem is at Line 14.

Try simulating the run of your program by hand for the iterations where i is 5, and then again for when i is 6. I bet you'll see the problem right away.

Ranajoy Saha
Ranch Hand

Joined: Jan 17, 2013
Posts: 33

posted

0

Sorry! I went off to sleep as I was not feeling well! I am really very sorry! Jesper de Jong ad Steven Miller thanks for answering to my query! Stevens's Miller did you mean to dry run the program? I read in class 8 and I am really confused what to do! If you please could asssit me with writing the corrected code then I will compare what mistake I was doing!

Ranajoy Saha
Ranch Hand

Joined: Jan 17, 2013
Posts: 33

posted

0

I got it! I will be calc += j Right! Cause each time when the rem == 0 is true the calc counter is increasing by the number it self it is not adding up the factors. But still I am getting the out put as "This number 1 is a perfect number." I cant make out why!

Ranajoy Saha
Ranch Hand

Joined: Jan 17, 2013
Posts: 33

posted

0

Thanks all the program is now fine and working very well! Thanks for the assist! May every user on this site live longer!

Ranajoy Saha wrote:I got it! I will be calc += j Right! Cause each time when the rem == 0 is true the calc counter is increasing by the number it self it is not adding up the factors.

Yes, that's it.

But still I am getting the out put as "This number 1 is a perfect number." I cant make out why!

Because 1 % 1 == 0. Look at line 9 and think about where you really want to start testing factors.

Ranajoy Saha
Ranch Hand

Joined: Jan 17, 2013
Posts: 33

posted

0

This is a more manipulated code that I wrote after correcting my mistake with the help of Jesper de Jong and Steve's Miller!

Good work! I see you fixed your problem with 1 by starting the outer loop at 2. That's a valid fix, but it doesn't test whether or not 1 is a perfect number. Since you know, in advance, that it is not a perfect number, you might want to add a comment that says so. Otherwise, the program isn't really testing every number in the range [1,500], which may be the assignment.

If you do make a comment about your reason for not starting your loop from 1 because you know it's not a perfect number, then you might as well think about your decision about the range of values you iterate through to check for proper divisors of a number. Why are you checking more than you need to? If you think about it, proper divisors of a number can only be up to half the number at most.

Junilu Lacar wrote:
If you do make a comment about your reason for not starting your loop from 1 because you know it's not a perfect number, then you might as well think about your decision about the range of values you iterate through to check for proper divisors of a number. Why are you checking more than you need to? If you think about it, proper divisors of a number can only be up to half the number at most.

These observations implicate a rather philosophical point: incorporation of a priori knowledge about the mathematics involved is a bit of a judgment call. Sure, it doesn't take much to realize that, if 1 is not a perfect number, then skipping 1 before you start iterating is a legitimate thing to incorporate into your code. Likewise, as no number has a factor bigger than its own half, ending your search for factors at half the number is also legitimate. But those are both decisions made on the basis of knowledge that is not incorporated into the algorithm the OP is using. And, if this is an assignment, those decisions may avoid meeting the goal. For example, if the assignment were, "Write a program that tests all numbers from 1 to 500, printing those that are perfect numbers," then starting your loop at 2 wouldn't meet the goal (because the program never tests 1). In an extreme case, if the assignment were, "Write a program that prints out all the perfect numbers in the range 1 to 500," one could submit this:

It's one thing to write a program that produces output you can verify; that includes any and all optimizations you can show, by extrinsic evidence, are consistent with the purpose of the program. It's another thing entirely to write a program that meets a particular spec.

Stevens Miller wrote:It's one thing to write a program that produces output you can verify; that includes any and all optimizations you can show, by extrinsic evidence, are consistent with the purpose of the program. It's another thing entirely to write a program that meets a particular spec.

Hmmm. You have to be a bit careful with stuff like that. Suppose you were asked to write a factorial program, what would you do for 0!?

The fact is that it's defined to be 1 (the best reason that I know of being that for every positive value of n, n! = n*(n-1)!), but I would say that it's equally valid for a person to write a program that throws an exception if 0 is supplied, or simply returns 1, because it doesn't fit the general pattern.
Along the same lines: is 1 a prime number? If you use the definition 'a number that is divisible only by itself and 1' then the answer must be true, yes? But it ain't.

The fact is that 0 and 1 are often exceptions to a general rule, so I think it's reasonable to use exceptional logic to deal with them.

Winston

Isn't it funny how there's always time and money enough to do it WRONG?
Articles by Winston can be found here

Both points are moot in the absence of a clear statement of the requirement. I do get your point about including 1 in the test range if the assignment/spec is clearly stated and interpreted the way you say. However, the leap from getting an answer via calculation vs. hard-coding the answer is hardly reasonable nor defensible, at least not with any professors I know (I don't know any law professors though - that might be a different story)

As for proper divisors being at most half the dividend, I don't see how the decision to use that mathematical fact can keep you from meeting the perfect number goal, no matter how it's stated.

Winston Gutkowski wrote:Suppose you were asked to write a factorial program, what would you do for 0!?

The fact is that it's defined to be 1 (the best reason that I know of being that for every positive value of n, n! = n*(n-1)!), but I would say that it's equally valid for a person to write a program that throws an exception if 0 is supplied, or simply returns 1, because it doesn't fit the general pattern.

I would disagree with you, then, Winston. 0! is, just as you say, defined to be 1. That's the value of 0!. The fact that an obvious algorithm that correctly computes n! for all n > 0 won't correctly compute 0! is irrelevant. The math is the math, regardless of what any particular algorithm can or cannot do.

One could easily concoct a more convincing example. Suppose I define f(x) over ther range [0,100] to be (x < 50 : x | x > 50 : x + 1 | x = 50 : 2.3). That is a perfectly valid mathematical function definition. Code that computed f(x) could take a lot of different forms, but I wager that most would include a specific test for x == 50, upon which the routine would just return 2.3. Nothing wrong or dodgy about that. My point is that the range (the set of possible parameters to the function) of perfect numbers is the positive integers: that includes 1, and the OP's program isn't testing it. Thus, his program is incomplete if the assignment was to compute all perfect numbers on the range [1,500], because his program doesn't test it. He's right to say 1 isn't perfect, but his program embeds that knowledge in its code, rather than proving by computation that the knowledge is correct.

Along the same lines: is 1 a prime number? If you use the definition 'a number that is divisible only by itself and 1' then the answer must be true, yes? But it ain't.

Well, if you use the definition, 'a number that is divisible only by itself and 1,' then you are not using the definition everyone else is using. See, part of a function's defintion is its range. More precisely, a function is defined for a particular range. For prime numbers, the definition applies to the range composed of the natural numbers greater than 1. 1 itself is not in that range, so the question, "Is 1 prime?" is answered in the negative, because the definition makes it ineligible.

The fact is that 0 and 1 are often exceptions to a general rule, so I think it's reasonable to use exceptional logic to deal with them.

Agreed! But you do have to deal with them. The code we're seeing here doesn't deal with 1, even though 1 is in the range covered by the definition of perfect numbers.

Think of it this way: suppose the assignment were to create a routine of the form, boolean isPerfect(int n) throws SomeException, returning true if n were perfect, false if it were not, and throwing SomeException if n is outside the range of perfect numbers. Would you have it throw an exception on n == 1? I would argue it should return false. But, either way, it has to handle n == 1, which the OP's code presently isn't doing.

Both points are moot in the absence of a clear statement of the requirement. I do get your point about including 1 in the test range if the assignment/spec is clearly stated and interpreted the way you say. However, the leap from getting an answer via calculation vs. hard-coding the answer is hardly reasonable nor defensible, at least not with any professors I know

Well, that's why I made those points. The "correctness" of the code depends on the spec. I would say it is, at the moment, unknown, rather than moot.

(I don't know any law professors though - that might be a different story)

Heh. As a senior in college, I took a Pascal course for which the final exam called for a program to print the first ten lines of Pascal's Triangle. One of my classmates was utterly baffled by the notion of doing so algorithmically, so he submitted ten println statements that correctly produced the first ten lines of Pascal's Triangle. As a second-semester senior himself, failng the exam would have been catastrophic. The professor grudgingly admitted that the question, as written, allowed for the answer he gave, and passed him. (My master's degree in CS came in very handy in law school, btw: you'd be surprised how many legal issues can be broken down into logical components with defined boundaries, exceptional cases, and necessary implications. My professors were actually very approving of that approach.)

As for proper divisors being at most half the dividend, I don't see how the decision to use that mathematical fact can keep you from meeting the perfect number goal, no matter how it's stated.

That one's a closer call. No number has a proper divisor greater than half itself, so excluding those seems only to be applying a pretty fundamental fact. Under the "explain your work" rubric of evaluating test answers, I'd want at least a comment there that showed the student had applied that fact knowingly, rather than somehow guessing at it. In grad school (CS, not law), my profs often made the point that, if your proof relied on some previously established theorem, you were free to skip the proof thereof, but you had to say something like, "because no number has a proper divisor greater than half itself," at least.

Of course, you're right that we don't have a statement of the problem other than what the OP wrote. I would just hate to think we were assisting someone in a way that helped him in one way, but left him dangling in another. (Come to think of it, there is a concept in American law to that effect: No one is under any obligation to rescue a person who is in trouble, but anyone who voluntarily undertakes to rescue someone must not, as a result of their efforts at rescue, leave that person in a worse position than they were in the first place. I have never studied other nation's laws, but I am told that is not the rule in most other systems. Go figure. )

Winston Gutkowski wrote:Along the same lines: is 1 a prime number? If you use the definition 'a number that is divisible only by itself and 1' then the answer must be true, yes? But it ain't.

Off topic, but here's the mathematical background for why 1 isn't considered a prime number:

There's a thing called the "Unique Factorization Theorem" which says that a positive integer can be represented as the product of prime factors in only one way. For example 102 is factorized as 2 * 3 * 17 and nohow else. So treating 1 as a prime number makes a mess of this, because now you could say 102 = 1 * 2 * 3 * 17, which is different. And when you generalize integers and primality to rings other than the integers, you find that there's a concept of "unit". Among the integers only 1 and -1 are units, but in other rings there can be more units. You can read the Wikipedia article Fundamental theorem of arithmetic if you want a better statement of the issues than what I said.

And yes, Stevens, mathematics and law are very similar in the way they work. I've always considered lawyers to be mathematicians who suffer from extroversion.

Stevens Miller wrote:The "correctness" of the code depends on the spec. I would say it is, at the moment, unknown, rather than moot.

I was referring to the points made as moot, as seen by the responses you've gotten, because the specific requirement/spec is unknown. Anyway, I won't try to debate that at length with a lawyer And mind you, don't try to debate math with Paul either, I've done that once before and it wasn't pretty (for me, that is).

Paul Clapham wrote:And yes, Stevens, mathematics and law are very similar in the way they work. I've always considered lawyers to be mathematicians who suffer from extroversion.

I don't know enough math to have an opinion on that, Paul. My impression is that law and computer science employ a lot of the same logical structures and, in particular, ways of testing the viability of an approach to a problem. I do wish more attorneys acted like mathematicians, however. It's one thing to be persuasive, but it's another altogether to show that a logically implied necessary condition has actually been met. (I tend to think of lawyers as being more akin to philosophers in the way that computer programmers are akin to mathematicians: philosophers and mathematicians operate in the realm of pure thought, making them prophets of the platonic absolute; lawyers and programmers operate in the realm of approximations to that purity, making them engineers of applied philosophy. You guys up on Olympus tell us where the limits are, the rest of us down here in the fields and vineyards try to make something out of what that allows. It's a good distribution labor, imho.)