mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

You don't have an implementation of setTime or getTime in the extClockType. The compiler assumes that the call refers to the setTime function in the base class ClockType and doesn't find a version of it with 4 parameters. Just implement a version of the setTime in the extClockType with the 4 parameters and it should work.

**Please use code tags in future posts**

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

You can use the getline() function. Notice in the link, that there is a parameter called delim which stands for a character that delimits your reading operation (it will stop reading in the string when it finds that character). By default, the delimiter is the newline character (and thus, the name "getline()"). To read, up to a comma, you can do this:

getline(myfile, n.lastname, ',');

But, since you can also stop at a colon, you will have to first extract up to the colon, and then extract the individual names from that string. That can be done with a stringstream object. As so, for example:

string str_up_to_colon;
getline(myfile,str_up_to_colon,':');
stringstream ss(str_up_to_colon);
while(!ss.eof()) {
  getline(ss, n.lastname, ',');
  getline(ss, n.firstname, ',');
  v1.push_back(n);
};

This might not work for all the cases that you have, but the examples above give you the basic tool set to use. If all fails, you can always use the myfile.get() function to extract each character one by one and construct your strings one character at a time.

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

The code that you used is correct in some sense. Whether the character that is displayed on the screen when you run the program is not a matter of how the program is written or how it is compiled. It is a matter of which environment you are running the program in. In your case, the program runs in a console (a.k.a. terminal or command prompt). These consoles use one type of encoding to translate the characters that are written from their binary (numerical) code to an actual character displayed. So, with that code you have, it would correctly be displayed if your console used an ascii unicode format, I guess it doesn't. Either try to change the coding to ascii unicode (via an option of your console window) or use the program that Red Goose posted to display all the characters and their corresponding numerical value. If either fails (i.e. you can't change it to ascii unicode, and you cannot find the cent symbol), you can try to use wide characters instead (16bit in length). For this, you will have to figure out what encoding your console is using by looking it up on the internet, find the code for the cent character in that encoding, and then use wchar_t instead of char in your code.

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

You'll have to be more precise. Mapping? What do you mean:
- Mapping as in Map-Making (like Magellan!)
- Mapping as in functional or topological mappings in mathematics
- Mapping as in mapping some keys to some elements (as in std::map)
- Mapping as in memory-mapped pointers
- ....

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

>>why not explain where and how they are normally used in bigger programs(programs that use API, GUI or more than a console window)?

HANDLE is a standard Windows pointer type. If you go to msdn.microsoft.com and make a search for "HANDLE" under win32 API, you will find 495,000 hits (just about every function in the win32 API). Is that enough examples for you?

Qt is a cross-platform tool for building GUIs, in that framework, almost every significant piece of the GUI is stored and used via a pointer to it. This is mainly because of polymorphism in OOP. Although they often use smart-pointers too (which you may or may not consider to be a pointer).

The vast majority of libraries that you can use via DLLs or shared libraries have C-style interfaces that pass pointers to-and-fro their API functions (like Win32 does). A simple example is FreeImage that is a library used to load, manipulate and save any image file format. When you want to access the image's data (like pixels), you call a function, get a pointer back, and dereference the pointer to access the data. A huge number of libraries work in a very similar way.

..... blablabla .... the number of examples of real-life uses of pointers is uncountable. They are ubiquitous. They are only (almost) avoidable in open-architecture projects (basically a library with which you interact directly with the source code of the library and not with an API or …

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

Your LoadData is an array of double (floating-point values, not integral values) and so, picking an element of it with LoadData[count+1] gives a value that is of type double and you use that value as a size for the new array MemLocation, but a size has to be an integral value. So, the compiler might implicitly convert the double to an integral type (in this case unsigned int) but will also issue a warning because it usually does not make sense to convert a double to an int and it is often not how you would like the conversion to be done (it doesn't round-off the number, it just truncates all the decimals, even if the value is 1.999999, it still will convert to 1 as an integer). So, if you are always using this LoadData to store integral numbers, make it an array of integral types (int or unsigned int) but not an array of doubles.

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

>>LoadData[count+1]
This is a variable of type double. You cannot use a double as the number of elements in an array, you can only have an integral number of elements (i.e. no fractional number of elements!). You need to either convert it to an integer or change the LoadData array to an integer array.

>>would the rest of the file be written with zeros, or would it have the remainder of the original file still there?

It depends. If you open the file with the flag std::ios::append, whatever you write in the file will be written at the end of whatever was there before. If you open the file without the append flag, then the entire content of the file will be deleted and it will start writing the new content from the start of an empty file. So, in your example, if the file has 26 chars and you write 14 chars. If the file was opened with "append", then the final file will have 40 chars. If the file was opened without "append", then the final file will have 14 chars only. In other words, the default behaviour is "overwrite" and the append flag lets you add content to the file.

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

>>Something obvious I'm missing?
Yes. At line 19 and 22, in the cases, you use the characters '1' and '2'. These are not equal to the numbers 1 and 2. The characters '1' and '2' are ASCII characters corresponding to the actual numbers 49 and 50 (look-up "ascii table"). So, you should not use those single quote marks around the numbers and it should work fine.

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

You forgot to change all the types to const char*:

/***************************************************
  The following program will take user's input
  and check whether it is in the following language:

    <S> --->  a <B> | <A> | b
    <A> --->  c <A> |  c
    <B> --->  d | <A>
****************************************************/


#include<iostream>
#include<string>
using namespace std;
#include<stdlib.h>  // for the exit(1) function


const char* SProd(const char* ThisOne ); // <S> --> a <B>  | <A>  | b
const char* AProd(const char* ThisOne ); // <A> --> c <A>  | c
const char* BProd(const char* ThisOne ); // <B> --> d      | <A>
const char* XProd(const char* ThisOne, const char x);

int main()
{


	string text;

	 cout<<"Enter a string"<<endl;
	 cin>>text;


    //*ThisOne = text.begin();
     const char* ThisOne = text.c_str();
	 ThisOne = SProd(ThisOne);


	if(*ThisOne== '\0')  //Check whether there is an extra character at the end
		cout<<"valid"<<endl;
	else
		cout<<"Invalid"<<endl;
	system("pause");
   	return 0;
}



const char* XProd(const char* ThisOne, const char x)
{
		ThisOne = XProd(ThisOne, 'a');
		ThisOne	 = XProd(ThisOne, 'b');
		ThisOne   = XProd(ThisOne, 'c');
		ThisOne	 = XProd(ThisOne,  'd');
		return ThisOne;
}

 // <S> --> a <B>  | <A>  | b
const char* SProd(const char* ThisOne ) //notice const here.
{
	if (*ThisOne == 'b')
	{
		ThisOne++;
		return ThisOne;
	}

	else {
		if (*ThisOne == 'a')
	{
		ThisOne++;
		  ThisOne =   BProd(ThisOne);
		 return ThisOne;
	}
		else
		{
		  ThisOne =   AProd( ThisOne);
			 return ThisOne;
		}
	}
}




// <A> --> c <A>  | c
const char* AProd(const char* ThisOne) //notice const here.
{
	if(*ThisOne != 'c')
	{
		cout<<"Invalid"<<endl;
		exit(1);
	} …
mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

For an offline version, you can probably google around and find some version of it (might not be the exactly appropriate one, but it usually should be). For example, here you can download all the STL documentation in a zip or tarball (as offline html files) (it doesn't include iostreams and string functions and classes, only STL containers and algorithms).

EDIT: I also found this one which seems to be fairly complete, recent enough and from a trusted source (IBM).

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

As said, if you look on any page at http://www.cplusplus.com/reference/ say this one on vector for example, you will find in the top right corner the #include needed for this class or function (in the case of vector, it is #include <vector>, if that wasn't obvious enough already).

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

at lines 70 and 75, remove the "const char" part, it is not valid C++ syntax.

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

You need to take out the line number 27 (i.e. the previous declaration of ThisOne). And you need to make all your return types "const char*" (not only the parameter types like you did) as in:

const char* XProd(const char* ThisOne, const char x); //notice the const at the start.
//...
const char* XProd(const char* ThisOne, const char x) //notice the const at the start.
{
		ThisOne = XProd(ThisOne, 'a');
		ThisOne	 = XProd(ThisOne, 'b');
		ThisOne   = XProd(ThisOne, 'c');
		ThisOne	 = XProd(ThisOne,  'd');
		return ThisOne;
}

Just do the same for all the other functions.

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

I'm not sure I understand what you mean with the whole interpreted language application stuff.

But, all you need to make that little snippet of code work is to forward-declare the types. Specifically, you can add the following at the very beginning of the code you posted:

class b; //forward-declaration of class b.

And your code will compile just fine.

I don't know if that solves your real problem, but it answers the question you asked.

fishsicles commented: Thanks for the forward-declaration aid! +1
mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

Well, one things that is annoying is that the code you posted has the same error that my early post was addressing (which is that you are doing a shallow-copy when you should be doing a deep-copy). You do understand that this code will crash:

int main() {
  int* ptr1 = new int;
  int* ptr2 = ptr1;
  delete ptr1;
  delete ptr2; //CRASH!
};

In the above, since both ptr1 and ptr2 point to the same location, you cannot call delete on both of them because as soon as one delete is called, both pointers are invalid and trying to call delete on either one of them will cause a crash.

In your code, the problem is exactly the same. You cannot make a copy of a pointer such that you end-up with two pointers pointing to the same location and then calling delete on both, whichever gets deleted second will cause a crash.
So, as a basic solution, you should try this:

#include <iostream>
#include <exception>

class A  {
protected:
   int x;
   int arr[10];   
public:
   A (int n) : x(n) {
      for (int q=0;q<10;q++)  {
         arr[q]=q;
       }
    }
   A () : x(0) {}
   virtual ~A () {} 
   A (const A& cpy)  {
      x=cpy.x;
      for (int q=0;q<10;q++)  {
         arr[q]=cpy.arr[q];
       }
    }
   A& operator= (const A& cpy)  {
      x=cpy.x;
      for (int q=0;q<10;q++)  {
         arr[q]=cpy.arr[q];
       }
      return *this;
    }
   
   friend std::ostream& operator<< (std::ostream& outp,const A& obj)  {
      for (int q=0;q<10;q++)  {
         outp << obj.arr[q] << "\t";
       }
      return outp …
mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

That's much much worse than the first program you posted. I mean, the first program is fine. It works except for that tiny one-line mistake. The code you just posted now is far from even compiling.

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

May I suggest that you read the following explanation.

One solution to your problem is explicit instantiation of the template. Here is an example of a function template. This is, of course, only applicable if you have a reasonably small amount of predetermined types for which your template could be instantiated. In real-life, this technique will make the compilation of the template code take a very long time, but it will make all the code that use that template code very fast to compile.

mitrious commented: Offered a pretty complete solution and really useful info +1
mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

Ok, so after you have copied a pointer, the two copies will of course point to the same address, i.e. the same variable or object or array. That's the idea. So of course, in my little code snippet, *a_ptr_copy will evaluate to 42, because that is the value of a_variable. The purpose of that snippet was just to illustrate that there are situations in which you can have pointers to objects or variables or arrays that were not allocated from the heap and so the compiler cannot assume that.

And also, a pointer is a record of the address in memory of "something". When you copy a pointer, you could do it because you want to hold a second record of the address in memory of that same "something", or you could do it because you want to have a pointer to a new "something". The compiler has to behave consistently and cannot infer as to what you "meant to do" it can only do what you tell it to do. So, in this case, the compiler will always assume that when you copy a pointer, you are holding a second record of the address in memory of the same "something" as the original pointer had. When you think about it, it has to be that way, otherwise it would be a mess (note that there are programming languages that implement the inverse behaviour (copy a pointer = copy the memory).. and they are a mess).

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

Zjarek is correct.
And the error message is related to the fact that the use of [] without anything inside of it is only permitted in a few cases (when declaring a parameter to a function or when declaring a static array whose size is determined by its initializer), in all other cases, the compiler expects you to put something in-between (i.e. an index) and when it does not find it, it throws an error "expected primary-expression".

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

To do this in better style, you should do the following two changes:
1) Your line 33 should be:

const char* ThisOne = text.c_str();

And eliminating the declaration of ThisOne, earlier.

2) change all your parameter and return types from "char*" to "const char*".

That should fix it. And you will get null-terminated string from this c_str() function (but the price to pay is that you cannot modify that null-terminated string, and thus, all those "const" keywords to declare that you won't touch the actual values of the characters... which from a quick scan of your code, seems to be the case).

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

Consider this simple piece of code:

int main() {
  int a_variable = 42;
  int* a_ptr = &a_variable;
  int* a_ptr_cpy = a_ptr; 
};

Now, if I understand you correctly, you are puzzled by the fact that when you copy a pointer, it doesn't make a copy of the memory it points to. Although it could have been implemented that way, it is not. The reason it is not, is because a pointer could point to anything (could be an object allocated on the stack, it could be an object allocated on the heap, it could be the start of an array, it could be just some value that is not an address but was casted to a pointer type... etc. etc.). The compiler cannot make assumptions like "oh, this pointer clearly points to an object allocated on the heap and that object is not from some other derived class" and then decide to make that memory copy for you. It is your responsibility to handle this correctly based on what you know. A pointer is just a address value, nothing else (of course, the address value is the address of something meaningful, but for the compiler, a pointer is not much more than an integer that holds an address in memory).

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

I think that you meant to enclose lines 6 and 7 into a { } brackets (because as is, the pop_back function will be called even though the vector is empty).

As for the push function, I don't get it. Why is it necessary for the vector to be non-empty? How would you fill the stack in the first place if you forbid the pushing of an element when it's empty. I think that if-statement should just disappear.

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

>>Do you know exactly how it's done?
No. The instruction set is not put in the processor, it's intrinsic to the processor (depending on what exactly you consider the processor).

I have to stop you there though. You might be willing to go down to the fundamentals laws of the Universe, but I'm not. I have very limited knowledge of how processors work, but I have enough to be satisfied and understand its working principles (which is not needed to do programming btw).

This thread is extremely out of topic. This is a C++ forum. You ought to take this to some processor design forum (if one even exists).

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

>>//I can't come up with something better than this
You need to implement deep-copy semantics. The default copy-constructor, which is exactly like the code you put, will perform a shallow-copy. This means it simply makes the pointer y point to the same object as the cpy.y pointer. You will get an exception because when the first object gets deleted, it also deletes its y pointer, and when you reach the destructor of the second object, it will again try to delete its y pointer which is now invalid. Using the shared_ptr will solve this problem automagically by implementing shared ownership semantics (i.e. all copies of an object share ownership of the object pointed to by their y pointer), the shared_ptr will only deleted the pointed-to object when all object of class B that have a pointer to that object have been deleted. However, if shared ownership is not what you want, i.e. you want each object of class B to have a unique y pointer pointing to a unique object for each B-object. Then you need deep-copy semantics, which means that a new object of class A is created for the new copy and that that object is copied... as follows:

B(const B& cpy) : A(cpy) {
    delete y; //you must delete the old y in order to not leave a memory leak.
    y = new A(*cpy.y); //create a new copy of *cpy.y.
  };

Now, if that y pointer is not actually pointing to an object of class …

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

>>// Am I right to pass it just by its name? Will the constructor know its name?
No. Inside the body of a member function, the object itself is accessible via the "this" pointer. This is a pointer to the instance of the class that was attached to the call to the member function. To turn that pointer to a value or reference, you just need the dereferencing operator, as such:

TheData::TheData()
{
	Valid = false;
	Length = 0;
	Values = 0;
	TheMenu::MainMenu(*this); // *this dereferences the this pointer to make it a reference (or value).
}

>>// I can still use the same name right?
Yes. Because DataIn from main() is only visible in the main() function, there is no problem in reusing the same name as the parameter name. In fact, if it is a good name that describes the purpose of the variable, then it is preferable that you use that name for the parameter. But, it does not have to be the same name, it can be any name that you want and the name you choose in the definition of the function is the name that you need to use to use that parameter within that function.

>>// This little bit, does that create a class object called DataOut?
Yes. That creates a global object of class TheData with the name DataOut. Since it is global, it is accessible anywhere. This is ok, but considered bad programming practice (both the …

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

>>Plus, you didn't even add any function to hold the window open so I had to add
That's just a thing that is specific for Windows and when you are running it from an IDE like Visual Studio or Code.Blocks. I'm using Linux, and I had no way of knowing what you are using.

>>it's just that it makes very little sense to me.
You have to do your part too. First, read the definition of a pointer. Then, read the definition of a reference. Then ask yourself, in the code that I posted, why is it so that the first two function calls change the value of my_var in the main() function, and why the last function call does not even though all three functions have the same implementation.

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

>>Homework?
If it is allowed to use vector for the homework, then it is a really easy homework.

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

>>"passed in the function, it can get modified"

You can compile and run this to see:

#include <iostream>

void pass_by_pointer(int* ptr) { 
  *ptr = 42;
};

void pass_by_reference(int& ref) {
  ref = 69;
};

void pass_by_value(int value) {
  value = 187;
};

int main() {
  int my_var = 0;
  std::cout << "the value of my_var is " << my_var << std::endl;
  pass_by_pointer(&my_var);
  std::cout << "the value of my_var is now " << my_var << std::endl;
  pass_by_reference(my_var);
  std::cout << "the value of my_var is now " << my_var << std::endl;
  pass_by_value(my_var);
  std::cout << "the value of my_var is now " << my_var << std::endl;
  return 0;
};

That should make it clear. Btw, the syntax is:

int Foo; // declares a variable named Foo, of type int.
int* Foo; // declares a pointer named Foo that points to a variable of type int.
int& Foo; // declares a reference named Foo to a variable of type int.

>>"I could go old mother nature style and use wooden stakes and steel and stone materials to carve, develop and hardwire things myself with out the involvement of other companies or factions."

You are aware that steel is not found in nature. It is manufactured (and not particularly easy to make). So you do acknowledge that _some_ use of things that others have developed is OK. It is a matter of deciding what. You can go back to the stone age and start from scratch, but not using the expertise, …

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

**Please use code tags**

I don't really understand your question. The vector class in the STL is already an implementation of a stack (in fact almost all basic STL containers are). With either vector or list:
- to push an element on the stack, you use push_back()
- to pop an element off the stack, you use pop_back()
- to access the element on top of the stack, you use back()
That's all there is to it. If you want more "stack-like" vocabulary, you can use the stack class of the STL. This just wraps an STL container with the above functions into a class that has functions that are characteristic of a stack. So, to use vector for a stack, you do this:

#include <vector>
#include <stack>
#include <iostream>
using namespace std;

int main() {
  stack< int, vector<int> > my_stack; //now, this is a stack stored in a vector.
  my_stack.push(42);
  cout << my_stack.top() << endl;
  my_stack.pop();
  if(my_stack.empty())
    cout << "the stack is now empty." << endl;
  return 0;
};

I don't know why you would want to make your own stack class, but if you still do. Then make question more precise and read the STL documentation well, it usually contains all the answers and examples needed.

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

>>I thought that because main() doesn't end yet, all the members and variables that were created inside it would still be available to all the other functions in the program.

You're logic is correct but there is another aspect that you are neglecting. Yes, variables that you declare in main are available as long as main has not finished (and that would be true for any function or { } block). However, the variables declared in the main function are not _visible_ or _accessible_ to any other parts of the program besides the main function. Visibility of variables have to be limited, otherwise it would be horribly difficult to make sure that you refer to the correct variables and also it introduces an crazy mix between the caller and callee contexts.

If you want access to a variable in a function it has to be either declared in that function, passed as a parameter to the function, or a global variable (or static data member of a class which is basically also a global variable). So these are the options:

//as a variable declared in the function:
void f() {
  int my_var = 42;
  cout << "my_var is: " << my_var << endl; //my_var is accessible in f() because it was declared in f().
};
int main() {
  f();
  return 0;
};

//as a passed parameter:
void f(int my_param) { //now my_param is a variable in f(), with the value my_var from main()
  cout << "my_param is: …
NichtSoGut commented: So much information, I've learnt loads because of it!! +6
mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

>>"//this should be safe" in fact holds no such guarantee.
It is made safe by the fact that the pointer is in the private scope of the class B and that all the constructors of B make the pointer either NULL or valid. So, I say "this should be safe" not because of the trivial if-statement before, but because of the addition of y(NULL) to the default constructor. I thought that was clear from my explanation, I guess it wasn't, thanks for pointing it out.

>>just note, deleting NULL is defined and does nothing. So that if statement isn't necessary.
Thanks for pointing that out, it has been a while since I have actually used raw pointers (or even an actual delete statement). Also worth pointing out, not all implementations are really standard when you get down to the details of, I developed a habit of checking for NULL on pointers because I had to use an old Borland compiler that caused a crash if a null-pointer was deleted.

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

I would go one step further than gerard4143, I would say that it is not only O.K., but considered better practice in C++ to declare variables only where they are needed. In theory, it is faster. In practice it is just nicer because it keeps things localized in the code. If you have, for example, a large algorithm in one function and it requires many temporary or helper variables to do the various mathematical manipulations it needs. If you put all the variable declarations at the beginning, when someone reads you code, every time he encounters a new variable name he will have to visually scan through possibly the entire algorithm to see if that variable is meaningful in the algorithm or just a temporary. If it is declared on-site and within a reduced scope (like an "if" statement or inner-loop) then it is clear that it is a temporary or helper variable that is not relevant to the overall algorithm but just used to perform a local operation. Also, reduction of the scope of the variables can lead to better performance and will reduce the stack usage in a large function (i.e. if you have all variables at the start, the compiler has to generate an unecessarily large stack frame for that function, and every memory access operation will potentially be more costly if the stack is too large. While local declarations will make the stack frame be incrementally increased as the scopes of the function are encountered, and …

Aranarth commented: Indeed. +1
mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

You are doing it correctly. Except, you are not giving a value to the y pointer when you are creating the object of class B without parameters (i.e. in the default constructor). This would mean that your pointer y will have an uninitialized (and thus invalid) value and deleting that invalid pointer would raise an exception or run-time error of some kind (depending on OS and compiler settings).

This would be the "proper" way to do it:

class A {
protected:
   int somedata;
public:
   A () : somedata(0) {} //better never leave uninitialized data.
   A (int x) : somedata(x) {}
   virtual ~A () {} 
 };
class B : public virtual A { //note: you don't need virtual inheritance here!
   A* y;
public:   
   B () : y(NULL) {} //initialize to NULL if nothing better can be done.
   B (int x) : A(x), y(new A()) {} 
   ~B () {
     if(y) //verify that y is not NULL before deleting it.
       delete y; //this should be safe.
    }
  };

The virtual inheritance that you have is not really useful (at least not in this simple example), and it has some oddities to be aware of.

The easiest thing to do here is to use smart pointers. That just makes everything easier. You can find them in either TR1 (std::tr1 namespace) or the Boost smart pointer libraries (they have the same names and behaviour, except that "scoped_ptr" is called "unique_ptr" in TR1.. I think). A shared_ptr use in …

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

>>Do you enjoy ruining peoples' lives like that?
The truth is better than false illusions.

>>If I knew EXACTLY how the whole process was done in every instance I'd do it,
Where does this logic end? Have you thought about that? You seem to be saying: I don't want to use an existing programming language because I don't know exactly what it translates to in machine code... I don't want to use existing machine code because I don't know how it translates to module executions on the CPU... I don't want to use existing CPUs because I don't know how it translates to moving charge in the integrated circuit... I don't want to use existing integrated circuits because I don't know how they move electrons around... I don't want to use existing semi-conductors because I don't know how it translates to quantum physics processes... I don't want to use existing quantum physics theory because I don't know how it translates to the fundamental laws of the Universe... come on... this thought process gets ridiculous very quickly.

>>Plus, lying and making me think I might do it is better than outright saying I won't.
No, it's not. Your parents might not want to burst your bubble and destroy your hopes. But you have to get real someday.

>>And last, do you know how the whole ENTIRE process of it is done, say, from absolute scratch?
In broad terms, yes, in details, no. A processor …

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

>>Are you saying I couldn't possibly manage to create computer hardware myself and have that hardware only known by myself and use it to my advantage in every way?

Sure, you can create your own computer hardware. All you need is:
- a Ph.D. in semi-conductor physics and integrated circuits
- a grade 5000 clean room
- a silicon furnace and surface condenser
- high-precision etchers
- printed circuit board manufacturing facility (at least 16 layers)
- a Ph.D. in Thermodynamics, Heat Transfer, and Probabilistic Quantum Physics
- ....
- and 20 life-times!

You said "Microsoft did it with Windows so I can too". First of all, all microsoft started with was DOS, which was heavily inspired by Unix systems of the time. They didn't build computers, they didn't even come up with the programming language, not even a compiler. All they did, at first, was a small OS that used already existing platforms and standards (made by _other_ people). And, most importantly, it became a "good" OS because people found it practical and that grew there company, and with the combined expertise of all their employees, they developed increasingly complex software solutions and OSes.

The important thing here is "combined expertise". No one, in the field of computers or any other field in general, knows everything (and usually understands much less). It is all about trusting that the people who have expertise in one area can do their …

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

@Transcendant: If you are still having trouble with making this program work, I suggest you create a fresh new thread for it (because this thread seem to have about two posts related to the question out of 25 or so). I'm sorry (on "behalf" of daniweb) for the flame war that occurred on this thread. It is the first time I see this happen on this forum, and I hope it will not discourage you from posting questions again.

AndreRet commented: Cool +6
mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

If you want control over what you do, you need knowledge, understanding and practice, none of those come _easy_, none of those can be _complete_, and the search for them will _never_ _end_, you have to accept that before you can even start to learn to program.

A lot of the programming field of work (like many scientific fields of work) is about what you don't know, what you don't understand, and what you have little practical knowledge of, these are the things that should tickle you into wanting to seek to fill those gaps. If they are truly frightening you (as opposed to exciting you, like it does for me), then it might not be the best place for you.

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

About pointers, there are two "alternatives" (the quote marks mean that they really can't completely replace pointers, but can significantly reduce the need for them).

First, a very popular design pattern in C++ is RAII (Resource Allocation Is Initialization). This just means that when an object is created it initializes the resources it needs and when it gets destroyed it frees them. I warn you, this relies on encapsulation. A simple example is the std::vector class in STL versus C-style dynamic arrays which use raw pointers. Consider those two equivalent codes:

int main() {
  std::vector<int> my_array;  //creating the object my_array also initializes it to a valid state.
  my_array.resize(50);        //requesting my_array to have a new size of 50
  for(int i=0;i<50;++i)       //looping around to set the values
    my_array[i] = i;
  return 0;
};                            //here, my_array gets out-of-scope -> destroyed -> frees the array of integers

int main() {
  int* my_array;           //creating a raw pointer with invalid state
  my_array = new int[50];  //allocating memory for 50 integers and storing its address in my_array
  for(int i=0;i<50;++i)    //looping around to set the values
    my_array[i] = i;
  delete[] my_array;       //deleting the array manually is required to avoid a memory leak.
  return 0;
};

You see, because std::vector is uses the RAII principle, the first piece of code is much superior to the second because there are no point where an invalid state exists and the user of std::vector doesn't have to worry about memory leaks (or more generally, the management of the resource, e.g. …

Narue commented: I feel sorry for you. Your well-intentioned and excellent post fell on deaf ears. +25
StuXYZ commented: Excellent post in a strange thread +4
thelamb commented: *copy/paste Narue's reputation* +3
mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

I like this idea in principle, but I don't think that std::vector::erase() works with reverse_iterator . At least, my compiler doesn't like it.

Yes, this is a frustrating point with reverse_iterators, I don't understand why the STL has this reverse iterator class for almost all their containers but no overloads of their functions to also deal with reverse iterators. Basically, all you can do with a reverse iterator is traverse a "static" container (static in the sense you don't modify the structure of it). I find them nice, especially with <algorithm> . With some trickery, you can actually use them with erase(), but it is kinda nasty see this, here is an example that works (use -std=gnu++0x or -std=c++0x flags because of the lambda expressions):

#include <iostream>
#include <vector>
#include <algorithm>
#include <cmath>
#include <ctime>
using namespace std;

int main() {
  srand((unsigned int)time(0));
  vector<double> arr(20);
  cout << "The unsorted vector is:" << endl;
  generate(arr.begin(),arr.end(), []() -> double { double x = (rand() % 10000) * 0.001; 
                                                   cout << x << endl;
                                                   return x; } );
  
  sort(arr.begin(),arr.end());
  cout << "The sorted vector is:" << endl;
  for_each(arr.begin(),arr.end(), [](double x) { cout << x << endl; } );

  for(vector<double>::reverse_iterator rit = arr.rbegin(); rit != arr.rend(); ++rit)
    if(((*rit) < 7.0) && ((*rit) > 3.0)) //trim away numbers between 3 and 7
      rit = vector<double>::reverse_iterator(arr.erase(rit.base() - 1) + 1); //call erase with a reverse_iterator.. nasty..

  cout << "The trimmed vector is:" << endl;
  for_each(arr.begin(),arr.end(), [](double x) { cout << x << endl; …
mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

Three points to make here:
1) The error is caused by the fact that you are changing the size of the vector at line 67 by calling erase() on it. Once you change the size, the iterator is invalid. You could refrain from modifying the length of the vector in the loop or you could use the fact that the erase function returns an iterator to the element that is now at the place where the element that you erased used to be before it was removed. In other words, do this at line 67:

it = lengths.erase(it); //notice the "it = "

2) Definitely, you should use a reverse iterator for this, if you want your code to be robust. So, make the follow changes:

//at line 57:
std::vector< double >::reverse_iterator it = lengths.rbegin();
//at line 59:
while(it != lengths.rend()){
//at line 86:
++it;

3) If what you really need is the vector to be sorted from biggest to lowest numbers (and not the default from lowest to biggest), I would suggest you do so with the sorting algorithm, at line 46 (and you would need to #include <functional>):

std::sort(lengths.begin(), lengths.end(), std::greater<double>());

@Fbody>>An iterator is essentially just a templatized wrapper for a pointer.
You think too much. An iterator is an iterator and that's all you need to know. The fact that it most probably is just a (wrapped) pointer is a piece of information that is more harmful than anything else. You are …

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

>>Well the discussion was about mixing C with C++
Yeah, read my initial post.

>>but since C doesn't have those features, you can't argue with this point.
My point was that the more C that you use in C++, the less you are taking advantage of those features. If you restrict the conversation to things that can be done (almost) equivalently in either languages, then there isn't much to talk about, and it isn't so bad to mix C with C++ (see my initial post). And, btw, if you look at your list (raw pointer vs smart pointer, array vs containers, etc.), the reason why the C++ counterparts would be preferable is because they take advantage of the features that I mentioned, I was just generalizing your point from small (trivial) differences to more global software design difficulties that too much C in C++ would cause. From re-reading your posts, it seems that this was the point you were trying to make in the first place by calling C++ alternatives "safer" and promoting "consistency" in the coding style. I think that as long as the use of C-style code is trivial (like the extreme case of static casts) and that it is well encapsulated into good C++-style interfaces (not passing raw pointers and the like in public member functions), then it's fine to use some C code for the (hidden) implementations, but if it spills out of the interfaces it will pollute the C++ code and make …

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

Converting a double to an integer is not a trivial operation because they are represented completely differently in binary. It is not like conversions between integer types where it's almost just a matter of changing the number of bits. Like L7Sqr has reported, I would expect the conversion from double to integer to be taking a lot of the computing time (we're only talking about a few clock-cycles here, of course). If you can get away with not using floating-point values at all (which is very common in embedded systems since many micro-controllers don't have floating-point modules on their CPU anyways, or very limited capabilities for floating-point operations), then it will be faster. If it is appropriate, consider perhaps using integers with a mapping like 1(integer) -> 0.001(floating-point) (or even a base 2 mapping) and do all your calculation with integers only and your transcendental functions with look-up tables.

And, I would expect that the code you have would be faster than the sin() on a micro-controller (if that sin() function exists).

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

As for the GCC downloads, if it is still relevant to you:

gcc-4.5.2.tar.bz2 -> this is the compiler(s) and standard libraries (this is the one to download)
gcc-ada-4.5.2.tar.gz -> this has the ADA compiler (most probably useless to you)
gcc-testsuite-4.5.2.tar.gz -> this is if you want to test that GCC works correctly (don't worry about that.. don't download)

Enjoy your coding! And come back to Daniweb if you are having trouble!

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

If you have your own "home-brewed" project that you could make open-source, then what do you think is better on a résumé:

"I have worked on a little home project, and I think it's good."
OR
"I have started an open-source project, got several people on-board, managed to coordinate the work with them, and I even managed to get positive feedback from people who have used my code!"

I don't think that any employer would see the former as better than the latter. Of course, if you publish your code open-source, it also means that your potential employers will possibly take a look at it (I know I would). You run into the possibility that your code is not as good as you think and that might back-fire on you (it won't look good if you have an open-source project that includes no-one else and generally gets negative feedback).

Building a résumé is all about priorities. When you have little to show for, any little thing you have is good. Some years ago, I used to mention my home projects on the résumé or interview. Now, I have a lot more to put, so those are no longer included. I found that it is generally beneficial to at least show that you have some passion for what you do, and showing that you have spent a significant part of your free-time on home projects or an open-source one is a good way to show that. …

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

@Frederick2: From what I see, you are progressing. I might suggest you take a look at "C++ Coding Standards" by Alexandrescu and Sutter. You will understand why C++ standard libraries are programmed the way they are. You might also look around the Boost libraries for examples of awesome coding style. I am convinced it will speed up your transition to a more "purist" C++ style.

@firstPerson: The list you gave seem to me like pretty minor details too (just like Narue's cast example). Maybe these things can cause a few headaches (like segfaults) to a novice in C, and they surely would cause less grief when using the C++ counterparts. But to a mildly good programmer it won't make much of a difference except for maybe a bit of extra care with the C-style stuff (arrays, raw pointers and C-strings).

What I think is a much more pertinent problem with C is the lack of certain paramount features of C++:
- Resource Allocation Is Initialization (RAII)
- Enforcing interface usage through strong type constraints and access rights
- Generic algorithms with compile-time enforceable policies
- Avoiding name clashes via namespaces, nameless functors and lambdas.
- Modularity in general
... things of that nature (and I only wanted to mention those that are essentially impossible to reproduce in C, i.e. they need templates).

You can surely mix the benefits of the above features of C++ with some underlying …

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

There are many ways to mix C and C++.

1) It is very typical for external libraries to have C interfaces (API). There are many reasons why a C interface is chosen (or necessary). In that case, mixing C and C++ is required in order to use that external library, and it certainly is not considered bad style or whatever. This is normal and very typical.

2) You can literally have source files in C++ (.cpp files) and others in C (.c files) and have a build system that uses a C++ and C compiler to compile both and link everything. Generally, this happens when there are parts of the code that are very low-level (like hardware drivers) and thus, they tend to be more easily implemented in C because of less strict type-casting rules and stuff (also for legacy reasons). But, if the use of C source files is not justified, then it is usually considered somewhat bad to do this. Mainly, the hassle of compilation, linking, and cross-language headers (the infamous "extern "C" {") is annoying and since C is basically compilable on a C++ compiler it's usually not a big deal to just make the few fixes required for the C sources to be compilable as C++ source files and that saves a lot of hassle.

3) I suspect that what you are actually referring to by your question (and what Narue has answered to) is the use of C-style programming in C++ source …

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

I very often use the flush for displaying the simulation time without printing lines after lines. Say I run a numerical simulation in big loop, I would insert in it:

while (..) {
  //... all the simulation code
  //print the current simulation time over the last one printed (without a new line)
  std::cout << "\rCurrent time: " << std::setw(10) << sim_time;
  std::cout.flush(); //flush is required, otherwise, this would not work.
};

There are plenty of other situations where flushing a stream is useful (even more so when the stream is a file stream).

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

Just a thought. You could also use the Boost.Variant to solve your problem. Just return a boost::variant with all the possible image types. It's not pretty, but it'll work. Still better than violating type safety. If your image types are comparable in size, it might be a good alternative.

Personally, I think you ought to first take a step back and think of a redesign to avoid this problem altogether. The adaptor pattern and visitor pattern are usually useful when trying to pull external and poorly integrated code into your framework. Which is basically what Narue has already proposed. As an adaptor, you could code your own class that can contain and deal with any of the types of images you have (sort-of like a special purpose boost::variant class). As a visitor concept, you could isolate what transformations you need on the images and code a visitor class that can perform these transformations in a way that is tailored to each type, then all you need is a dummy base class for the image, use the RTTI to identify the type, and dispatch it to an appropriate visitor (this could be done with a MACRO or maybe in a Boost.Bind-like way).

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

You need to compile both cpp files in the same compilation:

$ g++ HelloApp.cpp Hello.cpp -Wall -o HelloApp

Or, on an IDE (like VS or Code.Blocks), you would need to add all the .cpp files to the list of "source files" for the project (or solution).

mike_2000_17 2,669 21st Century Viking Team Colleague Featured Poster

If your intarray is of type "long long int", I'm guessing that "begllts" and "endllts" are not. You should ask yourself why you are comparing values of different type. Maybe "begllts" and "endllts" should also be of type "long long int", or maybe the comparison is not logical, or maybe the variables simply need to be cast to "long long int" before, as so "(long long int)(begllts)".