I'm having problems figuring out if i should use pointers or references in certain methods
I have a method called issueOrders(Orders* order) which takes a reference to an Orders object
This method should add the pointer to order to a vector containing pointers to orders
void Player::issueOrder(Orders* order)
{
ordersList->getOrdersList().push_back(order);
}
where ordersList is an object containing a vector of ordersList as parameter
Like this:
class OrdersList{
private :
vector<Orders*> ordersList
public:
vector<Orders*> getOrdersList();
}
But the issueOrders method doesnt work, that is, nothing is pushed in the vector and im confused as to why.
Thanks for reading and any help is appreciated! :)
As #UnholySheep pointed out, your getter returns a copy of the ordersList vector. What you want is a reference (or a pointer), so that your push_backs affect the vector. So you want to change its declaration to this:
vector<Orders*>& getOrdersList();
And change its definition accordingly.
Whether or not you should store your Orders as pointers or references has nothing to do with the problem. And as the correct answer to the question in your title is largely dependent on the type of the data and the way it's going to be used, it's hard to give you an answer with just the code snippets. I suggest you take a look at this answer: https://stackoverflow.com/a/8259173/13191576
So here is my goal, I would like to instantiate an object based on a string and an integer. My current thought was this:
1) Create a list of possible objects
2) Each object has a static method that takes a string and integer and returns true, if what was passed matches the static members that object.
3) Then iterate over the list of possible objects, call the static function of that object if it returns true then instantiate that particular object:
pseudocode:
// Pseudo Definitions
class CoolObject
class CoolObject2: public CoolObject ....
class CoolObject3: public CoolObject ....
// List of Objects
std::list<CoolObject> list_of_possible_objects;
list_of_possible_objects.push_back(CoolObject);
list_of_possible_objects.push_back(CoolObject2);
list_of_possible_objects.push_back(CoolObject3);
// Inside of the matching function
for (std::list<CoolObject>::iterator it=list_of_possible_objects.begin(); it != list_of_possible_objects.end(); it++) {
if(*it::is_cool_object(string, int)) {
return *it(string1, string2); //Assume the constructor takes some objects that were passed into the function
}
}
However, this seems like a dream since C++ does not allow to have objects that are not instantiated.
I am sure I can do this with some kinda map and a switch statement but this seemed lot more elegant in my head so I went for it first.
Is there any pattern out there that is similar to this, that I can follow? Or is there a way to make what I am asking be legal?
I would rather not maintain a huge map and I would rather just have a list of objects and ask each object if its the one and then instantiate, if having a huge map and a switch statement is the only way, thats fine. I thought maybe ask some gurus, if this is possible or is there a better way of doing it before giving up on this way.
Thanks for all the help!
Store std::optional<T>, that's probably what you're looking for: basically just a flag to tell if the object is constructed and a reference to the object iff constructed. Note that you can't spare the flag, as you need to know whether to run the destructor or not.
I'm sure it was already answered here, but can't find it...
Say, a function has a parameter which is a reference to an STL vector. Sometimes the function has to fill out the vector, sometimes it does not. How can I let the function know when it should not fill out the vector? If the parameter was a pointer, then calling the function with null/not-null pointer would do the job. Is it possible to do the same with references without using pointers or additional parameters?
Added: What If I use the following function call:
func( std::vector<int>() );
And function header is:
func( std::vector<int>() &vec )
{...}
When how is it going to work? I've seen this trick in the real code. Does it mean the function still performs an action on the vector, but the caller should not bother about creating a vector in his code?
This doesn't necessarily qualify as a best practice, but it can be done. Ordinarily an optional parameter is specified with a pointer instead of a reference. But you can create a sentinel object that has special meaning to your function.
static std::vector<MyStuff> MyVecNull;
void MyFunc(std::vector<MyStuff>& vec = MyVecNull)
{
if (&vec != &MyVecNull) // only do the following if a vector was passed...
You could use two different functions.
Personally, I prefer using references as a light-weight way to pass a large read-only object, and pointers if I'm going to change the object. That way the call has the & right on it to show that we're going to change that object.
I have a vector of class objects I've created in main by reading in a data file. I'm then passing around the vector to several different files containing functions that perform different operations on the vector (sorting by different fields, subtracting inventory, etc.). I'm running into a problem when I try to use push_back to add to the vector in another file (that's a part of the same project) after it's already been created. The pre-existing vector is passed to the function and the vector is successfully added to within the function, but when I exit the function the added record is no longer there, and, as far as I can tell, I should be accessing the updated vector after that point forward from all my different functions in different files, right? I shouldn't have to pass the updated vector back if it's the same name as the one I created in main, should I? I'm sure the language and terminology I'm using are wrong (and please feel free to correct me), but it's almost as if the vector isn't updating globally and is only updating locally within the function for the duration of its call.
This is the function definition and code within the function I'm using where I want to add to the vector (I'm skipping all the variable parameter assignments for the sake of brevity). All of the functions I'm pointing to are the setter functions within the class, and prior to this point the vector already contains 20 records, and was set up similarly to the below function.
void addBook(vector<BookData> books)
{
BookData *books1;
books1 = new BookData;
books1->setTitle(bookTitle);
books1->setAuthor(author);
books1->setPub(publisher);
books1->setIsbn(isbn);
books1->setWholesale(wholesale);
books1->setRetail(retail);
books1->setQty(qtyOnHand);
books1->setDateAdded(dateAdded);
books.push_back(*books1);
}
I didn't want to flood the post with too much code but I can post more if it'd be helpful. I just want the additions (or deletions I make in another function) to be accessible throughout the whole program.
You should pass the vector by reference to modify the original global vector.
void addBook(vector<BookData>& books)
^^^
Otherwise you are passing a copy of the original vector to the function and modifying that not the global version.
You need to pass your vector as a reference wherever necessary. In that specific instance, you just need to change
void addBook(vector<BookData> books)
to:
void addBook(vector<BookData>& books)
otherwise your function gets a copy of the vector, not a reference to the original one.
let's say I want my users to use only one class, say SpecialData.
Now, this data class would have many methods, and depending on the type of data, the methods do different things, internally, but return externally similar results. Therefore my wanting to have one "public" class and other "private", child classes that would change the behavior of methods, etc...
It would be amazingly more simple for some types of data that need to be built to do something like this:
SpecialData& sm = SpecialData::new_supermatrix();
and new_supermatrix() would return a SuperMatrix instance, which inherits from most behaviors of SpecialData.
my header:
static SpecialData& new_supermatrix();
my cpp:
SpecialData& SpecialData::new_supermatrix()(){
return SuperMatrix(MATRIX_DEFAULT_MAGNITUDE,1000,1239,FLOAT32,etc...);
}
The problem is, I get this error, which is probably logical due to the circumstances:
invalid initialization of non-const reference of type ‘SpecialData&’ from a temporary of type ‘SpecialData’
So, any ideas?
Well, you've got three choices:
a) You want to have only one instance of SuperMatrix anyway. Then go for the static function member route as has already been suggested.
b) You want to create multiple instances. Then you have to return a pointer instead of references and create the objects with with new (i.e. return new SuperMatrix(...).
c) As an alternative to option b, you can also return merely an object, i.e.
SpecialData SpecialData::new_supermatrix()(){
return SuperMatrix(MATRIX_DEFAULT_MAGNITUDE,1000,1239,FLOAT32,etc...);
}
However, this requires a (deep-)copy operator (the default one won't suffice more often than not), and it means that the object is created on the stack, then copied and that copy is being returned. The good thing is, this won't leak memory if you don't actually receive the result into a variable. The bad thing is, if the object is very large, this can be very memory- and time-consuming.
Whatever you are going to do with it, these solutions are mutually exclusive, both technically and logically. ;)
Simple answer - you can't use references like that. Your new_supermatrix function returns a nameless temporary value which you try to bind to a non-const reference - C++ only allows such values to be bound to const references. If you want to write functions like this, you need to make them return a pointer to a dynamically allocated object, or stick with returning a value, but assign the return value to another value in the calling code.
This code has several problems. First of all, you probably want to use pointers here instead of references. Returning a reference to an object created on the stack like you do in your new_supermatrix will lead to a crash almost immediately. It needs to be allocated with new and passed back as a pointer if that's what you want but I'm not exactly sure what you're trying to do. But anyway, this is what's causing your error, you're returning a reference to a temporary variable.
You need to actually use the new operator. The creation you get by return SuperMatrix(MATRIX_DEFAULT_MAGNITUDE,1000,1239,FLOAT32,etc...); allocates the object on the stack, which is cleaned up when the function returns (which it is doing in the same line). Using new causes it to be allocated on the heap.
In your method, you can use a static:
SpecialData& SpecialData::new_supermatrix()(){
static SuperMatrix supermatrix(MATRIX_DEFAULT_MAGNITUDE,1000,1239,FLOAT32,etc...);
return supermatrix;
}
You must not return a reference to a temporary/local object.
This and many other common errors-to-be-avoided are explained in Meyers' book, Effective C++.
You're returning a reference to a temporary object, which is bad news, since once your method exits, the object doesn't exist anymore.
Read up on creational design patterns. The one that looks closest to what you want to do is the Factory Method pattern.