StuXYZ 731 Practically a Master Poster

First off there is not enough code provided to actually compile this. However, if the only error was that you are getting array overrun I am absolutely surprised.

The likely error is to do with deletion, and the use of bare-pointers in std::vectors.

E.g. Consider struct Population. Now that takes a DNA pointer and delete it. You have no copy constructor so you will have simple copy by value system, therefore you will have multiple delete of each copy of DNA* pChrome. That is particularly important for vectors since there are often extra copies and deletes in the construction and push_back as the memory is reallocated.


I am terrified of what GeneticAlgorithm does in its deletion operator, m_v_parentPop2 is not deleted but m_vPopulation2 is?

Next you are changing the size of m_vPopulatioin2 by using push_back but not adjusting the other sizes, e.g m_iDensity. BUT then you are using the size of m_vPopulation as a loop control variable -- a certain error at some point, since m_iDensity is too small.

In all, you have a big base of code that simply is buggy and interconnected to sort out. The best thing to do is to start again, and put it together bit by bit, but test each section, e.g. use vectors for all arrays, and check that the size of ALL arrays match. Check that nothing is every double deleted, nothing is not deleted. Write a register class for memory locations, or use a …

Fbody commented: Nice catch on the pointer. +4
Ancient Dragon commented: nice help :) +34
StuXYZ 731 Practically a Master Poster

Well first off, ALWAYS write a constructor, a copy constructor, an assignment operator and a destructor unless you are 100% absolutely certain you don't have to. If you have to think about it for even a second, write them all.

Therefore, what happens, well size is not initialized. [nor is list]. But you then allocate memory completely randomly. Also when do you get rid of it?

You MUST write a default constructor and a destructor and most of your problems will go away.

In addition: you are using namespace std; and then using a variable called "list". This is 99.99% certain to trip you up soon. Since you have a list object in std. Please just don't use that "using" construct, sure use a smaller form, e.g. using std::cout; etc , or just use std::cout.

You have errors in remove(), you copy list[y+1] when y can get to the end of the array. Obvious, memory corruption, particularly if your template type has its own copy constructor.

Finally, make print put a std::endl; onto std::cout when you have finished writing.

StuXYZ 731 Practically a Master Poster

Ok in the first instance, using power is plain ugly and inefficient. The typical route for a polynomial in the positive sense, is to do something like this:

int total(0);
int xpow(1);
for(int i=0;i<=degree;i++)
  {
    total+=coef[i]*xpow;
    xpow*=x;
   }

You can also do it via an internal bracket expansion: [this is effectively (((coef[N]*x+coef[N-1])*x+coef[N-2])*x+.... ))) ]

int total(0);
for(int i=degree;i>0;i--)
  {
    total+=coef[i];
    total*=x;
  }
total+=coef[0];

I like the second one slightly more.... but not alot in it. [Note the fact you are counting down in the loop, AND you cannot save a step by initializing the total to coef[0] before the loop. -- I only emphasize the last point as ran a 2000 CPU hour simulation with that bug in it :(. ]


Your display function is wrong because you write coef[0] twice, run the loop for(int i=1;i<degree;i++) . Note that it is normal to write polynomials high power to constant.

Your multiply: If you want to limit the degree to less than 100, then as well as a warning exit as well. Also have your resized coefs??? in temp do you zero coefs in temp ???

Note: Mike_2000_17 beat me to the post [must learn to type faster], sorry for the repeat, the second version of the evaluation code might be of merit, however.

p.s. Thanks for posting a good first post question to the C++ forum, e.g. code blocks, and sufficient information about your problem and what you have tried.

peterman.k commented: Very helpful +1
StuXYZ 731 Practically a Master Poster

Firstly, obviously you can see that you don't need any template specialization for this example. But assuming that this is a example, let us see what you did wrong.
It is just that sloppy practices that are allowed in non-template code are not allowed when dealing with templates.


(a) for a template function you must have a declaration .
(b) You cannot add a double to a pointer so start and stop should be int/unsigned int etc.
(c) you have to put the default initializer in the declaration.

// Put a declaration of the generic version [ALWAYS].
template<typename T> T sum(T*,int,int,T =T());

template<>
int sum<int>(int* array, int start, int stop, int init)
{
  int* stp = (array + stop);
  int* str = (array + start);
  while(str != stp)
    {
      init += *str++;
    }
  return init;
}

// If the type can be deduced then there is not need to write 
// the type
template<>
double sum(double* array, int start, int stop, double init)
{
  double* stp = (array + stop);
  double* str = (array + start);
  while(str != stp)
    {
      init += *str++;
    }
  return init;
}


int main()
{
  int a[] = {1,2,3,4,5,6,7,8,9};
  
  cout << sum(a, 2, 9,0)<<std::endl;
  cout << sum<>(a, 2, 9,0)<<std::endl;
  cout << sum<int>(a, 2, 9,0)<<std::endl;
}

Note that three ways to call sum. They are all allowed because the type can be deduced. If the template type was only the return type, then you would have to explicitly put …

Agni commented: Helpful +3
StuXYZ 731 Practically a Master Poster

You MUST make sure that each call to a new , is matched by one and only one call to a delete.

So looking at your code, you put the delete after 289 before 290.

I really don't like the goto. It is called AFTER the program has finished, but, before you have exited the mainloop. Its effect is to prevent normal exiting of the program.

Calling a function from itself, is ok IF and ONLY IF, you have a way to get out.
This is wrong for example:

void function()
{
   // Stuff...
   function();
}

Were as this would be ok:

void function(count)
{
   if (count<0) return; 
   // stuff
   function(count-1);
}

Note the early termination in the second version.
What you have created is an endless loop, which allocates a small amount of extra memory each time through. Therefore I am unhappy with it. It is perfectly good, if you call it a set number of times, then exit. But make sure you have an exit.

StuXYZ 731 Practically a Master Poster

Not surprising because of a tiny bug in your loop: You wrote: for( int inte = 1; inte = 1; ) { } Now a for loop has four parts, first an initializer, that goes from the first open bracket to the semi-colon. Second a conditional, that goes between the first and second semi colon, Next is post iteration statement, that goes after the second semi-colon. Finally there is the loop block that goes between the two braces { }.

The loop is done this way.
(a) Carry out whatever is in the initialization statement
(b) Test the conditional.
-- If the conditional is FALSE : leave the loop block -- Do nothing more.
-- if the conditional is TRUE : continue to (c)
(c) Execute the loop block.
(d) Execute the loop iteration statement
(e) goto (b).

So in your case:
(a) you create an integer inte. Then it is set to 1.
(b) Determine that inte=1 is TRUE. That is because ALL integer assignments of any value other than 0 are true.
(c) execute loop block
(d) Nothing to do
(e) Go to (b)

Thus you can never get out of your loop. That is why 34/35 dont get run.

Also please please call your variables something slightly more descriptive, using inte, integ intege is asking to make a typo and cause piles of difficulty finding the bug.

StuXYZ 731 Practically a Master Poster

There are several very worring things to think about.

The first is the delete [] pixels_index that happens on line 58 of your original code and line 261 of the update. That line gets called a lot of times if I am not mistaken, but you only create pixels_index once. To test it, put a std::cout<<"this is called only once "<<std::endl; and make sure I am wrong.

Second, the goto refresh command, that is going to produces a huge stack, at each time, you are getting an extra loop. You should loop over the flush ONLY while there are events on the queue, then you should stop.

Other than that I can't see anything, hopefully, that is the problem or someone else can see what is wrong...

StuXYZ 731 Practically a Master Poster

Sorry, you haven't given us enough code here...

We need to know what w, w_temp, h_temp get assigned to and how. If you can, post the
fragment of code that they are set in as well please.

I guess the you almost certainly have made a memory error with the indexes e.g. by overwriting global_index when it comes to the last value because of the +2 etc.

The other thing I am thinking of is that you have not initialized one of those variables?

StuXYZ 731 Practically a Master Poster

Ok first off, welcome to daniweb, and thank you for writing a clear post with code blocks and not-too much and not too little code!

Ok to your problem, you have unfortunately made a couple of logic errors. First, consider your loop, for(int c=2;c<= num;c++) . This will test each possible factor up and including the number itself. If this was the only error, ALL of your test numbers [except 2] would be reported as not-prime.

Now, let us consider the inner part of the loop, numPrime is set true each and every time round the loop. Then it is set if a factor is found. BUT then it is tested, and regardless if it is either true/false you execute a break statement. Therefore,you only test if the number divides by 2. No other numbers. You can see this if you add a line cout<<"Test number c == "<<c<<endl; as the first instruction of the loop.

So to remedy you could do something like this

numPrime=true;
for(int c=2;c<num;c++)
   {
     if (num % c == 0) 
       {
          numPrime=false;
          break;
       }
   }

  if (numPrime == true) 
    std::cout<<"Number prime"<<std::endl;
  else
    std::cout<<"Number not prime"<<std::endl;

Some simple improvements that will help, you only need to test up to the square root
of the number, since if a*b=N^2 and a=N+x and b=N+y where x, y and >=0 then
a*b== N^2 + N(x+y) +xy. Which can only hold if x,y==0.

StuXYZ 731 Practically a Master Poster

First off please use code tags.

Second, actually, this is quite a common and slightly difficult problem, and is 100% down to how numbers are represented on a computer.

First off float is an inaccurate number, it cannot represent even simple number, like 0.2 without some rounding error, that is because it is a set of binary values, e.g. to represent say 0.25 , we say that the number (in binary) is 001 and there are two shifts of the decimal point, e.g. the number read from RIGHT to LEFT: units, 1/2, 1/4, 1/8 etc... However there is no non-infinite sequence that represents many simple decimals, e.g. 0.2. [This is a gross simplification, see e.g. http://en.wikipedia.org/wiki/IEEE_754-2008 ]

The code you gave does this: total = (A-B)*100; where A and B are floating point numbers. Then you multiply but 100. What you have done in increase the error by a factor 100. [Note in binary that is a shift of over 6 bits.]

Then you have the other problem, you convert your floating point number to an integer like this : int I=A; . Now what is important is now that this simple cuts off all the decimal part, e.g. 2.999999 is converted to 2.

Then you say you got it working with the new code, actually, you just reduced the error and got luckier. The code you have is STILL in error, just that there are LESS cases. You will get errors for …

StuXYZ 731 Practically a Master Poster

Your problem is the equals sign (=) in your sort function.
You cannot e.g. this allows

Edge1 A(0,0,1);
Edge1 B(0,0,1); 

// This should not be true to use the algorithm sort.
sortFunction(&A,&B) == sortFunction(&B,&A)

Also please use a managed point with vectors, e.g. boost::shared_ptr.

tommyz4 commented: Good help. +0
StuXYZ 731 Practically a Master Poster

Two quick comments, AD is correct that you should have deleted line 4 in Fraction.h, [and that you have misspelled fractions in main()] (what it does is define the symbol hbg_cmpsc122 as and empty value. Therefore when you write namespace hbg_cmpsc122 { you have effectively writen namespace { .

This is why you have all the error messages to the unnamed namespace.

The normal include file guard, is to write this

#ifndef FRACTION_H
#define FRACTION_H

 // your stuff here...

#endif

So perhaps it would be better to change line 4 of Fraction.h to #define FRACTION_H .

Finally, if you want to turn warnings on for g++ then use g++ -W -Wall.

Ancient Dragon commented: Yes, that's what I meant :) +33
StuXYZ 731 Practically a Master Poster

Introductory Note: You have not written std::vector<double*> S; . Which is a completely different discussion. This is often frowned on because it is SO easy to mess up, the memory [de]allocations.


Ok: In the general sense it is perfectly fine to have a point to a vector, or any other stl class. There are several "obvious" reasons for having a pointer, e.g.
(a) you could have extended a standard class and have a polymorphic system.
(b) you have a selection of classes and were avoiding a bit of memory/resource etc.
(c) You want to transfer ownership of the pointer between objects.

Of those I think (a) and (b) are not good reasons:
(a) isn't good, since the lack of virtual functions in the STL implementations don't make them easy classes to extend.
(b) The size of the class is minimal relative to a filled class. Normally has zero bearing on memory footprint etc.
(c) I am kind of ok with, but I would normally wrap it in another class, with better control and semantics.

Now let us look at what you are actually doing and see if I agree.

Well every student has a vector<double> assignment, so you are only interesting in option (c). Indeed this does make your sort quicker. However, the cost is the potential bugs that you will introduce.
However you can effectively have what you want (and slightly more optimization), by moving the …

gerard4143 commented: Great pointers +4
StuXYZ 731 Practically a Master Poster

First off I assume that this is a course work/self-learning problem, otherwise, just use a pre-existing library routine. [GSL/ACM/G4 and others]

The usual place to look for maths stuff is the wolfram site and you get: http://mathworld.wolfram.com/QuarticEquation.html

Ok, that takes you through the solution of both the real and complex cases (constants a to e can be real/complex). [The real case is just a quick optimization of the complex case].

HOWEVER:

If you have coded up quadratic and cubic equations before and understand how the solvers work then you will have no problems. If you haven't done them before, ensure:
(i) You understand how they work [remember that your solver will have to do that in the case that constant a is zero.]
(ii) you have written and tested each of them
(iiI) You understand the special cases of the simpler equations

Your quadratic solver will use the lower level solvers for many of the special cases, e.g.
for the case that the depressed function has a zero x term. You cannot bluntly ignore the zero coefficient terms and just pretend that you want to solve it with the general form. It will give you divide by zero errors, or horrific numerical errors if you try to set zero to a very small number.

The quartic equation has a lot of alternate cases, it becomes an ugly mess of "if statements", in C++, no matter how it is …

StuXYZ 731 Practically a Master Poster

My guess is that you have just landed on the chapter about arrays. I could tell you about the standard library, stuff like vector etc BUT I hope that is a later chapter.
In fact, I hope that you do this exercise, three times or something like that, using different storage systems each time.

Anyway Arrays:

You seem to have understood variables, and they are just names that are going to have a type and a value. You could write this:

std::string name1,name2,name3,name4;
std::cout<<"Enter 4 names"<<std::endl;

std::cin>>name1>>name2>>name3>>name4;

Now that is ok, but what if you wanted more than 4 names, say 100. That would be VERY laborious. So to get round that you can do this:

std::string arrayOfNames[25];
std::cout<<"Enter 25 names"<<std::endl;
for(int i=0;i<25;i++)
  std::cin>>arrayOfNames[i]<<std::endl;

Now as long as the part in the square bracket correspond to a number from 0 to 24, you have effectively found a way to write arrayOfNames23 or whatever the number is.

There are two points : (a) the index runs from 0 to 24 (b) if you get it wrong and put arrayOfNames[25] what happens is undefined. i.e you can get a completely random name or your program can core dump etc.

In addition, since c++ is a relatively low level language, you can see how the code arranged the memory in reality (and hence why the strange 0 to 24 pattern above).
Consider this:

int xArray[25];
std::cout<<"Memory location for xArray[0]="
          <<reinterpret_cast<long int>(xArray)<<std::endl; 

for(int i=0;i<25;i++)
  std::cout<<"Mem …
StuXYZ 731 Practically a Master Poster

Well I am going to try to give you part of the answer, others (more knowledgeable) will hopefully fill the details in. I am going to assume you are talking about class initializers.

So let us do this via examples, so consider:

class A 
{
  const int vInt;          // Must be initialized in constructors
  double V;                // Can be initialized in constructors
  const complexClass cX;   // Will be initialized in constructors
  otherClass* Lptr;          // Can be initialized in constructors

  public:

    A();

    static double calcValue(const int);
    double getLen() const;
};

In this example there are four variables and two are constant. There are a set of rules about what happens in each case. First of all, all the variables can be initialized in the constructor. e.g.

A::A() : vInt(5),V(3.4),cX(1,2,3),Lptr(new otherClass(4.5,"filename")
{}

As you can see all variables are initialized. Now please not that the order matters.
You can only access them in order. This will not provide the correct results:

A::A() : vInt(40),Lptr(new otherClass(4.5,"filename"),V(Lptr->getLen())
{}

Note that despite the order on the constructor definition, the order is as given in the class definition, i.e. the value of Lptr is set after V has been set. In this code the likely effect is a memory violation/core dump of some sort. (You do get compiler warnings on all modern compilers)

Also note that I have not initialized cX. That is ok if and only if, cX has a default contructor, that takes no values. If cX's …

StuXYZ 731 Practically a Master Poster

Assuming the problem is slightly more general you have a list of number e.g.
int items[]={4,4,4,4}; and you have a target number T.
Now you need to clarify the rules:

(i) are brackets acceptable: e.g. the given solution (4 / 4 + 4 )* 4 has to have brackets to get the problem to work. Since there is no solution that exists without that I guess you are allowing that.

If that is the case, the one way to approach the problem is to encode the operations and numbers on to a stack (reverse polish notation). Then you can iterate through the placement of a fixed number of operators and a fixed number of index values and
evaluate each step:
e.g. 1 2 3 + 4 * - ==> 1-(2+3)*4 =

Now it is just a matter of keeping the values in the list in order and iterating through the operators.

Finally, I don't think this is a good problem for recursion, simply because if the solution for some part is above/below the result it doesn't help, you could divide or subtract if you have an intermediate solution that is above the target. However, you CAN produce a recursive results. But it is has to implement a hidden stack.

Finally, what about a different language: this problem is very simple in lisp :-)

iamthwee commented: Lisp? I'll look into this. +12
StuXYZ 731 Practically a Master Poster

I feel I have a slightly different perspective on this. Yes learning C++ itself will not make you a cool GUI program, but the library routines can be called from C++. However, the libraries keep changing, that is because we have new hardware, better algorithms, different OS which to build on etc. However, the C++ itself seems to have a slower rate of evolution. That makes the knowledge of C++ much more valuable.

Second C++ becomes part of your tool base, in my field, a large amount of numerical code is C++, some older stuff in fortran, GUIs [not that many] are in well java/python/ C++ with Qt/C++ with gtkmm. Scripting languages, we have R, python , lua to name a few, but they all end up calling C++ routines.

Unfortunately what is now required to produce a project, is a LOT of tools and knowledge, and that is before we get to the domain specific knowledge, I certainly would not have a job unless my Quantum mech. was at least passable, and I guess that every field has a set of domain information. That said, because I can code, I get a lot easier ride than if I had to rely on my physics alone, it improves review scores, allows me to have a lot more project options and employment opportunities.

Additionally, C++ is a very very large language, and one of the advantages I see, is that I can readily grasp these other languages and …

Nulled commented: Helped me get out of a stump... Thank you. +0
Ancient Dragon commented: nice summary +31
StuXYZ 731 Practically a Master Poster

Your problem looks like a lack of an extern + a scope error

Let me explain. You seem to "effectively" want to do this

int main()
{
   int var(10);          // this variable is local to main NOT the program
}

void foo()
{
   int a=var;         // THIS will not compile.
}

This is not allowed. That is because main(), as will all funcitons, protects its scope. So how to get round the problem:

int var;    // NOTE ABOVE MAIN

int main()
{  
   var=10;
}

void foo()
{
   int a=var;     // THIS is ok IF foo()'s defining is in the SAME file as main.
}

Well what if you want to have two separate files : For that we need the extern keyword.

// File Main
void foo();  // declaration 
int var;

int main()
{
   var =10;
   foo();
}
// SECOND FILE
extern int var;          // Note the extern keyword.

void foo()
{  
   int a=var;           // this is now ok and will get the value 10.
}

Hope that helps and question/comment please ask

Ancient Dragon commented: well said +31
StuXYZ 731 Practically a Master Poster

Can I add two more comments to this excellent post.

When you have the first answer, you may well be asked a few more detailed questions about your problem. Please try to answer them. Even if you are certain it is not the problem [you can explain that if you like -- that will help everyone.] This lack of interactivity, seems to kill posts dead, even though the original poster (OP) replies.

Often, the act of asking the question, leads to you discovering the solution yourself. Please don't just make the thread solved, with a "found the problem", please take the trouble to tell us what you did wrong. Even if it is brain dead stupid, we may laugh, but we all have been there and done it [and in my case, I seem to continue to have BDS moments]. You certainly will earn a lot more respect for admitting the error than the "found the problem" post.

StuXYZ 731 Practically a Master Poster

You mistake is here: dynamicArr ( dynamicArr& arr) {myLinkedList(arr.data);} What is happening is this. You are calling the copy constructor that MUST construct everything in the class BEFORE it gets to the part in the { }.

In the { }, you construct a copy, but then it goes out of scope..., leaving you with an empty list.

So do this: dynamicArr(const dynamicArr& arr) : myLinkedList(arr.data) {} That way you will not have to construct an empty linked list

You will have to fix myLinkedList as well.

P.S. PLEASE write an assignment operator like this:

dynamicArr&
dynamicArr::operator=(const dynamicArr& A)
{
   if (this!=&A)
     {
       // Your stuff here
     }
   return *this;
}

ALWAYS write a copy and assignment operator for all classes that have any dynamic memory, and then for most other classes. [Note: if you don't think it will be used then put the definition in the private section of the class]

StuXYZ 731 Practically a Master Poster

I think the issue here is first to define "big". What does that mean to you, size of an OS kernel (2million lines) , size of a big application (500,000 lines) etc. That gives you an idea of how much time a rewrite will take.

Next define the problem, why do you care how it is written: is it because you are not confident in the results or it crashes often etc., are you extending it to something else or adding functionality, or maybe you need to maintain it in its current state and just fix use bugs, or do you need your users to understand the code. [The latter is encountered say in scientific software, when you may need the users to see that the code implements the algorithms correctly]

The you want to define how complex the field of the program is, is it highly mathematical were algorithmic errors are likely, or maybe numerical rounding errors etc, or is it simpler [in algorithmic complexity] e.g. a GUI.

Once you and we have some of those answers this discussion can go forward. I seem to think that you don't need a c++ standard but more likely to want a static analysis, e.g. like the converity systems [note: useful but very very expensive]

Beyond that, I agree with the posts above, there is no such thing as "the standard", but a lot of things in a code that make me worry and the first one is …

Ancient Dragon commented: agree +28
StuXYZ 731 Practically a Master Poster

Finally.... (I hope),

The rotation about the axis is better done this way.

Vector3
Quaternion::rotate(const Vector3& v) const
{
  Quaternion qV(0.0,v);   // Set the w part to 0, and the x,y,z to the vector v
  Quaternion RV=(*this) * RV* this->inverse();   // inverse: return the quaterion: w,(-x,-y,-z)
  return Vector3(RV.x,RV.y,RV.z);
}

The main reason for this is numerical accuracy. Note your input (for a rotation) is already out by 1e-4.

StuXYZ 731 Practically a Master Poster

firstperson:

No, it will call the copy construct since your are declaring the vector3 at that point. If you write this:

class AXX {
public:

  AXX() { std::cout<<"Constructor"<<std::endl; }
  AXX(const AXX&) { std::cout<<"Copy Constructor"<<std::endl;}
  AXX& operator=(const AXX& A) { std::cout<<"Assignment"<<std::endl; }
};

int main()
{
  AXX alpha;
  AXX beta=alpha
  alpha=beta;
}

And you get Constructor : Copy : Assignment .

Excizted commented: Thank you for helping and keep doing it. :) +1
StuXYZ 731 Practically a Master Poster

I am going to take a long long short here as to what is wrong;

You write

class Vector3
{
float y, z, x;
};

Note the order!! That worries me (slightly) since you are doing a copy construction
e.g. your line result=pre_result; will actually call the copy constructor and not the assignment operator (operator=).
The rule is that the components are initialized in order. Do you have some test that involves x,y,z in that order [e.g. a making the vector a unit vector etc.],

By this I means this doesn't work:

// WRONG:
Vector3(const Vector3& A) : x(A.x),y(A.y),z(A.z/sqrt(x*x+y*y))
{}

Gives junk result, since the order of initialization is y,z,x [in your case]

Addition to that I have you done a make clean . That is remade your vector class. Is it possible that you have missed the Vector3.h dependency from the Vector3.o in the Makefile. Then you have changed the order of x,y,z and then you get junk. If you delete all the .o files and remake, and it works you have just to find the dependency failure in your Makefile.

If you are using g++, you are using -Wall and you treat each warning as an error.

Finally, since you have a Vector3, why no create the quaternion with the Vector3 + W.

class Quaternion
{
  double w;
  Vector3 Qvec;
  public:
   // ..... 
};

Note that I have made your quaternion a double since any real use with …

StuXYZ 731 Practically a Master Poster

First off I commend you for investigating what I think is one of the most difficult classes to write. As always with a polynomial class, it is a case of compromises, and further improvements as scope and efficiency are improved.

There are a few aspects that I think the code would be better for.
First is that obviously polynomials are rarely integer, double or complex are common, and more interesting polynomials exist.

Second: Please don't do copy by value, use a copy by reference:

Polynomial minus ( Polynomial b )      // this copies a 100 integer array!!
{ }

it is better to write:

Polynomial minus(const Polynomial& B) const
{ }

I have added (a) constant and (b) B is copied by reference.

Finally, care needs to be taken with the degree. Often a polynomial system is being simplified. You would expect the degree to reduce in addition/subtraction. e.g
x^2+6x +3= 0 ; -x^2-4x+2=0 in addition make 2x+5=0 and the degree has reduced by one.

Basically, a polynomial class seems easy on the surface, but is horribly complex. There are significant problems along the way. Numerical issues abound, what do do about division, efficiency etc. Solutions, etc, special cases [quadratic->quintic],
and also do you want to handle 1/x etc.

What always seems to happen, is the the polynomial class is converted into a specialized polynomial class for the local use, and a different polynomial class ends up begin written for …

jonsca commented: Good suggestions Stu +4
StuXYZ 731 Practically a Master Poster

Ok this code made me laugh -- I had better explain.

So let us consider each line in turn [note i have expanded the formatting]

for(int=2;i<1000;i++)         // Simple loop
   {
      for(j=2;i/j;j++)        // Loop to do j=2 to j < i : it works because
                              // integer arithmetic is being used

The i/j uses the fact that integer division ignores the division remainder,
e.g. 5/2 == 1 but 3/4 ==0 . Just writing i/j also uses the fact that any integer other than 0 is true.

To see the effect of i/j consider this

i  j   i/j  
8  1    8     
8  2    4     
8  3    2     
8  4    2
8  5    1
8  6    1
8  7    1
8  8    1
8  9    0

Continuing

// continued from above:
if (!(i%j)) break;           // if j is a factor of i , exit the inner (j) loop.
if (j>(i/j))                 // Test to see if all possibilities for have been 
                             // used since you don't need to test beyond sqrt(i) 
                             // Anything beyond that means it must be a prime

Note that (j>(i/j)) is a way of saying j*j>i . I think that latter is clearer

Hope that helps...

I guess I was more surprised by the way the whole code was written in a divisional style.

StuXYZ 731 Practically a Master Poster

Can you post the compiler error, if you use -llua to link to the library then you need
to have the liblua.so available. Are youg getting the same error message as before?

Also you can't compile this gcc -llua code.cpp, it has to be g++ -llua code.cpp because you will miss other dependencies.

While you are checking things what version of liblua.so do you have, i.e what does liblua.so point to [it will be a symbolic link]

Finally, it is possible to be wrongly linking against different version to the version that is being included. If you have that possibility, then it can be tested by doing this: g++ code.cpp /usr/lib64/liblua.so were you have explicitly said which file you are going to link against. [note there is no -l in this method as you are directly linking].
You can find the liblua.so with the locate command.

If the problem is that you have two version of the liblua.so then you need to either remove one, or re-arrange your ld.so.conf file (normally in /etc/ld.so.conf) so that you get the correct version first, or use an explicit -L path e.g. -L/usr/lib64

StuXYZ 731 Practically a Master Poster

Just looked up how the world cup seeding works: It is actually that the top 7 nations + the hosts are seeded to avoid each other. So you have a situation were the sides with difficulty 3 are places into there own groups and then the others are seeded into the groups.

In that case the probability dependent on the host strength:
Host ==3 : 21%.
Host ==2 : 37%
Host ==1 : 44%
host ==0 : 46%

Interesting problem !

So given that SA are not exactly good, e.g. maybe 1, then we had a 44% chance of a group of death.

In the case that the host is a

StuXYZ 731 Practically a Master Poster

If you are going to use a C library in C++, you need to compile the headers in C
style. That is done like this:

#include <iostream>
extern "C" {
#include <lua.h>
#include <lualib.h>
#include <lauxlib.h>
}

int main()
{
    int s=0;
    lua_State *L = lua_open();
    // load the libs
    luaL_openlibs(L);
    //run a Lua scrip here
    luaL_dofile(L,"test.lua");
    lua_close(L);
    return 0;
}

To compile and built it use: g++ test.cpp -llua You may need to add a -I flag to point to the lua include directories and -L flag to point to your liblua.so library. [In your case, your lua files are in /usr/include and /usr/lib so it is highly unlikely that you will need the -I and -L flags]

StuXYZ 731 Practically a Master Poster

Ok well here goes 101 of code compilation on Linux with g++/gcc.

This is simplified from the actual process so after you understand this, there is another level of detail to see.

Basically you can think of code compilation in two stages:

(a) Producing an object file, that is taking your c++ code and turning each of your statements into machine code.

Before I go on, let me discuss that a bit. In your code if you write double a(1.5); a+=1.3; , the compiler (g++) can do this it reserves
a memory location for a, puts 1.5 in it, and the adds 1.3 to it. It writes this in the form of machine code. You can see the direct assembler that it corresponds to by
compiling your program with -S, but this will have a lot of other instructions in the code, but you can find your code.

However, what happens if you write this

#include <cmath>

double func(const double A)
{
 return 2*sin(A);
}

Now the sin function is only declared in <cmath>. You do not have its definition, so the compiler has to put a function call into the assembler, but it doesn't yet know what the definition of that call is.

(b) Now after the source code has been converted to objects, the compiler <em>links</em>
the code together. This is done by ordering the source code AND by ensuring that the links to functions declared in other …

jonsca commented: Always solid answers +4
miturian commented: very helpful (and friendly!) +1
StuXYZ 731 Practically a Master Poster

Try using a string stream:

std::ostringstream cx;

for(int i=1;i<10;i++)
{
  cx.str("");            // clear the stringstream
  cx<<"File"<<i<<".txt";
  std::string Filename=cx.str();
}

Obviously you have to do something with Filename but it has the basics.
Note that since I use a loop, you have to clear the stringstream on each pass.
[you can define the stringstream within the loop if you like].

Cowbox commented: The help worked, until the next error I faced :( :D +0
StuXYZ 731 Practically a Master Poster

First off: Well done of writing your first "big" class.

I have quick question, does the prime check work. E.g what if you have 3, which is prime? I think it give false which is wrong. Also you only need to test as far as the sqrt(N).

pow does not correctly handle negative exponents.

operator%=, operator*= etc normally return a self reference. E.g. Number&.

You might want to think about moving the base of the system from 10, which really under-uses the integer storage space, to something a lot bigger.


I would also like to comment that normally, operator< and operator> etc are implemented with reference to each other, that cuts down the amount of code drastically. E.g.

bool
Number::operator<=(const Number& A) const
{
   // I like this form: 
   return !(this->operator>(A));
  
   // You can write this as well
   return A > *this;
}

Overall, a good first try. IMHO numerical code is one of the most difficult areas since it has to be both efficient and absolutely correct in for an infinite set of inputs. Even if you limit yourself to a basic set of numbers [i.e. 0,1,large,infinity] and their negatives you have a test suite of some >300 tests.

Finally, the warnings are because you are doing this: for(int i=0;i<data.size();i++) . The compiler is 100% correct, if the size of data exceeds the storage of an integer then that is a runtime bug and infinite loop. It can fixed by …

StuXYZ 731 Practically a Master Poster

Sorry dustreader, but if you are going to be using the STL, do this:

// Assign players in any order (not random)
shuffle(players,players+10);

The code given is horrific. It has three vectors etc...

However Calyso8 is starting, so it is important for him/her to understand the algorithm and what the c++ is doing:

Let us look at the required algorithm you want 10 players to have a
fixed number of thing. So just like dealing out cards you start with
10 cards which have 5 innocent, 1 doctor, 3 mafia , 1 cop.

Then you deal the cards to each player.

In code that looks something like this:

// SET CARDS:
int players[10];  // Unassigned at the moment
int cards[10];
for(int i=0;i<5;i++)
   cards[i]=3;
cards[5]=1;  // doctor
cards[6]=2;  // cop
cards[7]=cards[8]=cards[9]=0; // mafia

// DEAL Cards:
int numCards=10;     // Number of cards left
for(int i=0;i<10;i++)   // loop over players  
   {
      
      const int cardNumber=rand() % numCards;
      player[i]=cards[cardNumber];
       // NOW the clever bit : Move the last card to the used slot.
      cards[cardNumber]=cards[numCards-1];
       numCards--;                  // subtract 1 from the number of cards
  }

// Done:

That can be "shortened" and you can optimize out a number of the varables but this is an attempt to allow you to see the algorithm.

StuXYZ 731 Practically a Master Poster

The general way to solve N equations of N unknows of ANY powers (e.g. x^5) is the use Bezout's method.
See:

http://www.mathpages.com/home/kmath544/kmath544.htm

(Also there is a lot of literature to improve the speed and numerical stability).

The method is highly tractable to code because as matrix is created and used to reduce the equations down one by one and reducing the number of variables one by one.

At the end of the method you are left with one polynomial in one which you solve by your favorite solving method [eg. the gnu scientific library : http://www.gnu.org/software/gsl/

The resultant polynomial can be of a relative high power, e.g three quadratics in three unknowns will result in a 16th order poynominal.

jonsca commented: Best suggestion +2
StuXYZ 731 Practically a Master Poster

The problem that you have is understanding how the ordering works.
(It is like the maths problems of multiply before addition. e.g 6*5+3 is 33 not 48 )

You have written

if (s[i] == 'a'||'A'||'e'||'E'||'i'||'I'||'o'||'O'||'u'||'U')

which is the same as

if ((s[i]=='a') || true || true || true)

Since each character ('A', 'O' ... ) is not zero, they each evaluate to true.
Thus it is very very unlikely to do what you think it does.

StuXYZ 731 Practically a Master Poster

So, the loop that I'm using is incorrect? But the program works perfectly...huhu...

No the program doesn't work ALWAYS:

Enter a=4.4 b=5.5 and then why does this not find the root at
4.493409 ?

Or -4 and 0.5 does not find the root at 0.


That is the problem with the loop, it fails as it skips over the singularities. This can be corrected .

The errors that exist are :
(a) If f(a) >0 and f(b)< 0 then it fails
(b) If f(x) within the range a -> b has a singularity it CAN fail [but not always].


Otherwise the program is kind of ok. It makes too many calls to f(x)
[cache the value and then use it in the fabs test.]

The algorithm is best tried with pen and paper and a graph.
use gnuplot and type plot tan(x)-x and you will see the mess that this function is.

StuXYZ 731 Practically a Master Poster

I know how bisection method works..It just that I don't know how that loop can make it work..

Well the real problem is that the loop does not work. Or more accurately only works for the specific instance when f(a) <0 and f(b) >0 and there is only one root between a and b.

To actually understand what is going on you are going to HAVE to go through it with a piece of paper.
(i) Draw the graph of tan(x)-x
(ii) Observe that it has multiple roots - near [TEX]\pm\pi/2 + n\pi[/TEX].
(iii) Observer the discontinuity at exactly [TEX]\pm\pi/2 + n\pi[/TEX].
(iv) Observe that for +ve x the discontinuity is on the right of the root and for -ve x it is on the left.
(v) Obsever that there is a root at x=0.

So in all tan(x)-x is an awful function to test first, use a polynominal, until you understand the method. [which doesn't have a root at x=0 since that always leads to lots of programming errors.]

Next: take the graph of your function and mark the variables a,b and x, on the x-axis. Just take three different pens/pencils and put them vertically on the correct x-axis point.

Step through the code adjusting the pens as the variables change.

In short bisection is the same as the childrens game, guess a number, were you are told higher and lower, you remember a, and b as the highest …

StuXYZ 731 Practically a Master Poster

The trouble is that advance does not return an iterator, AND the iterator
(i in your code), has to be double derefrenced because the iterator points to a pointer and hence the error message. You need:

advance(i,a);
if ( (*i)->getName()==someVar )
{
}

Note I have added the extra brackets for clarity.

HOWEVER : if you have lots of calls to the advance method you really would be better off with a vector, but you can obviously test the runtime performance.

Carrots commented: Thanks buddy! :) +1
StuXYZ 731 Practically a Master Poster

I understand for quick solutions you would follow AncientDragon's sage advice.
However, that always leaves a sour taste since I am sure your want to know how to do it:

So here goes

template<typename A>
struct printFunctor
{
   static void print(FILE*,const T& Obj) { }
};

template<>
struct printFunctor<int>
{
    static void print(FILE* fptr,const int& Obj) {  // stuff for int }
};
// and so on for each type

Then it is just printFunctor<T>::print(Fdata,image->m[v][u]); assuming that template object T exists, or you can write printFunctor<int>::print(Fdata,image->m[v][u]); as appropiate.

There are lots and lots and lots of cool variants of this principle.

ylchen commented: Thanks for the solution. +1
StuXYZ 731 Practically a Master Poster

Ok, for maths courses have a look at the MIT lecture page http://ocw.mit.edu/OcwWeb/Mathematics/index.htm.

The undergraduate stuff is a great revision guide and most of it I would expect anyone in the field to understand/know. This graduate stuff is a fantastic resource, anyone working with computational geometry will have a good grounding in a lot of this stuff. But there was lots here that I didn't understand as deeply when I went through it.

Note: Maths is not a "understand and know" subject. You should read a maths paper, and try to get an overview, then read it again and get a bit of a deeper understanding and again and again and each time you aim to get slightly more understanding.

However, it is particularly important to do the problems. If you don't do the problems you get a big gap between the stuff you think you know and the stuff you actually know.

Finally, I would like to say something upbeat but maths is hard, I think it is like playing a musical instrument, it requires serious work before you are competent.

StuXYZ 731 Practically a Master Poster

This code is a mess, and 99% is that it is mixed c and c++ , it has not been set out tidily so neither I nor you know what is going on.

Things to fix:

Why use malloc to allocate memory use int* wt=new int[5]; Then remember to delete that memory. You fail to do that in your code because if you get the the return NULL you will have made a memory leak.

The loop construction: for(int i=process[j++];i<=nProcess;i++) is 100% too complex. There are nProcess and process has n variables
so what about for(int i=0;i<nProcess;i++) So if process[0] is > nProcess you stop that is wrong.

Then further stangeness, j goes to 1 and stays there,so why write arrivalTime[j+1] so why no write arrivalTime[2] .

The next problem is that you write

if ((arrivalTime[j+1]+burstTime[j+1]) > 
		(arrivalTime[j+2]+burstTime[j+2]))
	      int temp=process[j+1];    
	    process[j+1]=process[j+2];
	    process[j+2]=temp;

Unfortunately, you declare temp again, and that MASKS the original temp. e.g consider this

int temp=1;
 if (1<2)
     int temp=4;    
    std::cout<<"Temp == "<<temp<<std::end;;

This piece of code prints 1 it does not print 4.

Finally, why pass nProcess when this routine only can deal with 4 entries.

StuXYZ 731 Practically a Master Poster

Indeed sfou, it is a method that is absolutely instinctive for most programmers. It is mainly mathematicians that have the big hang up with that sort of construct. They (and theoretical physists) have the most complex if constructs on the planet, they just seem to HATE repeated multiple action if constructs, you always get an if ( conditional) else if (conditional) else from them.

[Quick note: Nothing fundamentally wrong with the way they do if statements, just it is so distinctive ]

Second quick note: Please drop the system("pause") . It really really is evil.

paddowan34 commented: StuXYZ Rocks thanks for the info. +0
StuXYZ 731 Practically a Master Poster

As far as I understand the standard, this is not possible .

There are slightly upsetting work-arounds.

First: If you don't need the virtual aspect, this is easy use a template return type. Easy.

Second: If you require the virtual part you can then return A_1 from B_2::foo. [You can get one part to return a A_2/B_2]. And then you have to cast is up later, since you can write virtual A_1* foo() { return new A_2; } BUT I loath the dynamic_cast that is going to be required if A_1 and A_2 are not access only via virtual methods [e.g. A_1 is not an interface class].

However, IF you are accessing an object of B_2 via a virtual function , you have to expect that you will not get a A_2 point back and you will be accessing the points methods via virtual methods and the conversion to A_2 doesn't matter.

Anyway , not really a solution, just some random thoughts. Sorry

StuXYZ 731 Practically a Master Poster

I think that you have got confused with the syntax of declaration and implementation. So here is an example with most of the common things you will likely need. [Please ask if I have missed something]

class Non_Template
{
  // stuff here
public:

  // Class DEFINITION
  template<typename T>
  class some_Template
    {
    public:
       
      T obj;
      
      void setObj(const T&);
   };

  // Two diferent uses of the template
  some_Template<int> IObj; 
  some_Template<double> DObj;
  
};

// Declartion of a member function outside of the class  
template<class T> 
void Non_Template::some_Template<T>::setObj(const T& A)
{
  obj=A;
  return;
}

int
main()
{
  Non_Template X;
  X.DObj.setObj(4.5);    // accessing the member via the class
}

Note I made the template declaration AND the objects public, that was not necessary so change as you wish.

StuXYZ 731 Practically a Master Poster

The problem you have is temporary values and what happens to them:
I think this will be clear (I hope :)

The problem is that your are taking a copy of the value in the list. This does indeed correctly delete the object. BUT then you do v=0 rather
than *vertexListIterator = 0 ; . Now you access the value in the list, which you have not erased, and then you access the memory area that you have deleted BUT that memory space is marked as deleted but is unlikely to have been over written so you get valid results. If you had done lots of other operations then you might get different results.

Note that if the list was just list<int> and the values were 1,2,3, you would not expect this to change the list:

for(list<int>::iterator ai=L.begin();ai!=L.end();++ai)
{
    int x= *ai;
    x=4;             // This doesn't change anything in list
}

The normal process that would be not to use the temporary.

delete *vertexListIterator;
*vertexListIterator=0

Also please please don't use the C style casts, use a static_cast. That would remove any problems that might arise in-case the list turned out to be of a polymorphic class, and Vertex wasn't the base.

You use reinterpret_cast<long int> in the output of the pointer value to be printed.

schnell commented: Good Explaination +0
StuXYZ 731 Practically a Master Poster

First things first: Dont use system("Pause") it has been discussed to death here and everywhere on the web.

Second: The next problem is that you are using temp1 without initializing it. i.e every time you run the program it could start with a different value and you don't know what it is.

Third: you use a struct student, BUT by not having a constructor in this object all the variables DO NOT GET INITIALIZED. Therefore your have another problem.

Four: You really really need an array of students. it would make the code MUCH shorter.

Five : Semi colon after the while (ans=='y' || ans=='Y') ;
is wrong. because then the while does nothing, or loops indefinitely

Six: the reason that your class_ave does not work is that your pass three uninitialized variables. Then you have the logic wrong. Ok. Consider that you wish to pass up to three students, then temp_1 etc
should be the three values the students get.
You might chose to do that like this

// THIS IS IN YOUR MAIN:
class_ave(record1.total,record2.total,record2.total);

Note, the thing that is getting you mixed up is that the values or VARIABLES that you use to call the function are not the same names as are in the declaration of the function, you can equally call the function like this
class_ave(40,45,34);

Note that you have then made another error. Your values in are int. This is not correct, since you are taking an average percentage on …

StuXYZ 731 Practically a Master Poster

You seem to have two cin>>x in your code at lines 23 and 21. I would delete line 23.

I might make count and integer but that is minor.
you have remembered to initialize your variables which is good.

StuXYZ 731 Practically a Master Poster

Welcome to the real world. There is not free lunch.... sorry.
So
(a) either attend your classes and actually pay attention.
(b) decide that the class is not a good use of time and instead study some books in the library.
(c) Fail your degree/course.

But because this is the real world, I care very very little other than if you pick option (c), you just might be competing with me for a job, and then I will have a little smile on my face.

To go from zero knowledge to that assignment is about 10 hours of reading. (I would figure it is 6 lectures (50min) and corresponding work
(5 hours)). That is one long evening.

[Quick note: option (b) was taken by a a REALLY bright individual at my college and he did really well -- although his invidual exam marks had a huge distribution]

StuXYZ 731 Practically a Master Poster

You have forgotten to use the return value of flip(). If you did this if (flip()==1) . I think you would be a lot better than looking at your loop count varible.

If really helps lots to run you code on paper, with a list of variables when the code is small and you are beginning. They you would see why you only get one head.

It also helps to printout the results every turn.

tux4life commented: Good suggestion on the code runout on paper :) +23