|
oops, sorry i didn't realize that it didn't print out properly... let's try this again. i wasn't using the & sign though, what does that do?
struct COMPLEX
{
CString original;
int changed;
CString new;
};
struct INV
{
CString zValue;
int valence;
int dependence;
int layerNum;
CArray<COMPLEX, COMPLEX> complexes;
};
struct INVISIBLE
{
CArray<INV, INV> invisible;
};
|
|
|
|
|
these are the errors I get when I compile. I haven't done anything to my code other than adding the COMPLEX struct, and adding the CArray into the INV struct.
c:\program files\microsoft visual studio\vc98\mfc\include\afxtempl.h(255) : error C2558: struct 'INV' : no copy constructor available
c:\program files\microsoft visual studio\vc98\mfc\include\afxtempl.h(1566) : while compiling class-template member function 'struct INV __thiscall CArray<struct inv,struct="" inv="">::GetAt(int) const'
C:\Program Files\Microsoft Visual Studio\MyProjects\GUPIXWIN\DefineMatrixElementDialog.cpp(252) : error C2664: 'Add' : cannot convert parameter 1 from 'struct INV' to 'struct INV'
No copy constructor available for struct 'INV'
the one about adding is coming from this line:
ma_invisible.Add(invElement);
where ma_invisible is a CArray of INV structures and invElement is of type INV.
Does anyone have any ideas?
|
|
|
|
|
Like the errors say, try implementing a copy constructor inside the INV struct. This constructor is needed to implement a CArray of objects, unless you use the ampersand (&) as the second parameter of the CArray template instantation.
See any good C++ book for instructions on how copy constructors work.
-Antti Keskinen
----------------------------------------------
The definition of impossible is strictly dependant
on what we think is possible.
|
|
|
|
|
Antti Keskinen wrote:
unless you use the ampersand (&) as the second parameter of the CArray template instantation.
with which CArray would i use the & with? the complexes or invisible one? (or both?)
thanks.
|
|
|
|
|
I think you should use it with both. So that the first TYPE is the struct's identifier, and the next is a reference to it. The default implementation uses a constant reference. They would e.g. become as
CArray< INV, INV& > INVArray;
For simple objects and members of the MFC collection, the usage of the class name only in the second parameter of CArray instantation works, because most of the classes have both copy constructors and operator= implemented. I believe you used a ready source code piece as an example of implementing it, and thus did not consider this issue.
Perhaps it works with this alteration. I am not sure, I'd need to test it myself to see what it says.. But this is pretty much as far as I can help you. Perhaps you should create a small test project just to create several structures with CArrays inside them and them fiddle about with them for a little to see how they work ?
-Antti Keskinen
----------------------------------------------
The definition of impossible is strictly dependant
on what we think is possible.
|
|
|
|
|
Basically,
The first paramater is the type stored in the array, so type INV in this case, the second is the type used in method calls - INV& avoids having to make a copy of the INV struct for each method call in the template that takes type INV.
Your problem basically comes down to the fact that CArray doesnt have a copy constructor. Without the embedded CArray in the INV struct, the compiler would just provide a default copy constructor for the INV struct. With the embedded CArray, it can't do it, so you need to provide a copy construtor for your INV struct that does a value by value copy of the "complexes" CArray member, plus the other ones too. It's needed because methods like GetAt return by value - IE make a copy of the item in the array and return that.
|
|
|
|
|
Antti Keskinen wrote:
instructions on how copy constructors work.
Just adding the ampersand didn't seem to do it... so I think I have to go the way of using copy constructors.
I don't have access (at the moment at least) to any (good) C++ books, so I was going through the help section of ms vc++ and came across some information that is useful. now, the examples they gave in the article entitled: BUG: Error C2664 and C2582 While Using CArray Class uses an example where a class containing a CArray is nested within another class. This is similar to what i am doing, i think, except they are using classes, where i'm using structs.
How do I implement a copy constructor for a CArray which is embedded within a struct? For example, I believe the only copy constructor I have to create is for my 'complexArray' CArray, which is embedded in a structure... I'm pretty sure I can't just put the copy constructor within the structure, so I'm not sure where I should define this copy constructor...
Thanks for all your help eveyone!
|
|
|
|
|
You define a copy contstructor for the structure itself, not the array inside it.
If your application required a copy constructor for the CArray, you would require to derive from CArray and implement a new class yourself: in this way, you would be able to define it's copy constructor. But that is not what you need.
Here is an example on implementing a copy constructor for a struct:
struct MyStruct
{
public:
MyStruct(const MyStruct& oldStruct);<DIV>
int iInteger;
double dDouble;<DIV>
};<DIV>
MyStruct::MyStruct( const MyStruct& oldStruct )
{
} The struct works pretty much in a similar way as a class does, but it has it's limitations, like member functions and so on. The access-level specification at the start of the struct is just a precaution: structures are public by default.
-Antti Keskinen
----------------------------------------------
The definition of impossible is strictly dependant
on what we think is possible.
|
|
|
|
|
Just adding the & wont do it because functions like GetAt return by value, ie make a copy of what they return, so you need a copy constructor.
The & is just an optomisation that prevents all the function arguments in the template being passed by value, and therefor you needing to make a copy there too, so say if CArray had a template function called dosomething, like this:
template<type STORE_TYPE, type ARG_TYPE>
CArray::DoSomething(ARG_TYPE blah)
{
}
Here, the second paramater you specify to the template (INV& in this case) represents the type that is used in function calls. By saying INV refrence (ie with the &) rather than plain old INV, you avoid the complier having to make a copy of the passed in value every time a CArray method is called, quite significant if the INV is quite big, which it might be with it's embedded array.
To actually implmemnt the copy constructor, see post below for declaration, then in the declaration you copy each memeber of the passed in struct to the same memeber in the "this" struct, and in the case of the embedded array you will need to loop round each element in the passed in struct, then manually add it to the this struct.
You might be better going for STL as stated below, STL is much better at this sort of thing, and the MFC collection stuff was only really written because STL wasn't about/finised then.
Use stl::vector instead of CArray and you get a free copy constructor.
Use stl::set and you get other stuff too.
The only down side to STL is the documentation is total crap.
|
|
|
|
|
I made a little test project just to try this all out before actually implementing it in my own project. I created a separate header file that contains all my structures, and also this new copy constructor stuff. I have included this header file in CMainFrame. I'm getting link errors now when I compile, I looked everywhere for information on these errors yesterday and have come to the conclusion that things are being linked in the wrong order or something, but I wasn't able to actually fix the problem. This is what my new header file looks like (we'll call it MyStructures.h):
#include "afxtempl.h"
#include "stdafx.h"
..other structs defined here...
struct INV
{
public:
INV(const INV& oldStruct);
INV();
INV& operator=( const INV &s );
int number;
CArray<COMPLEX, COMPLEX&> complexArray;
};
//INV constructor
INV::INV()
{}
// Copy constructor implementation
INV::INV( const INV& oldStruct )
{
number = oldStruct.number;
//copy the complex array here
}
//operator= implementation
INV& INV::operator= ( const INV &s )
{
number = s.number;
//copy the complex array here
return *this;
}
..other structs defined here...
these are the errors i'm getting:
MainFrm.obj : error LNK2005: "public: __thiscall INV::INV(void)" (??0INV@@QAE@XZ) already defined in CopyConstructorTest.obj
MainFrm.obj : error LNK2005: "public: __thiscall INV::INV(struct INV const &)" (??0INV@@QAE@ABU0@@Z) already defined in CopyConstructorTest.obj
MainFrm.obj : error LNK2005: "public: struct INV & __thiscall INV::operator=(struct INV const &)" (??4INV@@QAEAAU0@ABU0@@Z) already defined in CopyConstructorTest.obj
Debug/CopyConstructorTest.exe : fatal error LNK1169: one or more multiply defined symbols found
|
|
|
|
|
i seem to have fixed it now. i'm not sure if it's the correct solution, but it seems to work. all i did was move the INV constructor, copy constructor and operator= implementation into CMainFrame.
if that's not the right way to fix this problem, someone please let me know!
|
|
|
|
|
something completely different with your purpose, but, be careful on the names you give to your fields...
<font style="color:blue;">struct</font> COMPLEX {
CString original;
<font style="color:blue;">int</font> changed;
<font style="color:red;">CString new</font>;
};
new is a reserved name !!!
TOXCCT
|
|
|
|
|
toxcct wrote:
new is a reserved name !!!
yeah, i know that. That was actually just an example i had typed directly into this message board, i hadn't cut and pasted it. when i did it in my code, i used newStr instead. but thanks for picking up on that!
|
|
|
|
|
CArray is crap. You can certainly do this with vectors, vector being actual C++ as opposed to MFC overstretching it's limits.
Christian
I have drunk the cool-aid and found it wan and bitter. - Chris Maunder
|
|
|
|
|
why some program when i compile it is not error but execute it the error ' debug assertion failed'....Is anyone can let me know what is the program!!!!!
|
|
|
|
|
We often use _assert, ATLASSERT, ASSERT or similar macros to check for certain conditions being true (or false). These will provide confidence that previous code has worked.
However, these are not evaluated at compile-time, but at run-time. If you use MFC, there are many common messages, and under the debugger, if you select 'Retry', it will take you to the assert that triggered. Often that is enough to help you work out what went wrong.
Steve S
|
|
|
|
|
I would like to add that some times ASSERT is applied in MFC when it would cause no problems, since the SDK method/function being called just returns with fialure/success value. Therefore, you should detemine if it realy is an error (are you checking return value).
Example:
Many methods/functions that take an HDC as an argument and will accept a NULL HDC (use screen DC instead).
For the most part MFC takes the above situation into account, but occationaly they did let a few through. In which case, the assert becomes an information only assert.
INTP
|
|
|
|
|
Hi!
I am currently trying to display small images in a dialog using a CStatic. I've created a static control in the dialog using the resource editor and set its style to SS_BITMAP. Then I created a variable for the static, m_stcImagePreview (type CStatic).
Then I tried to set the image using this code:
IMAGEINFO ii;
VERIFY(m_pParentImageList->GetImageInfo(m_nIconId, &ii));
m_stcImagePreview.SetBitmap(ii.hbmImage); It doesn't throw an assertion error, but unfortunately it also doesn't work... The image isn't displayed, it shows random crap. The m_pParentImageList is a pointer to the image list containing some 16x16 images, it is assured that m_nIconId is never greater than the image count.
Any idea what I am doing wrong?
Dominik
_outp(0x64, 0xAD);
and
__asm mov al, 0xAD __asm out 0x64, al
do the same... but what do they do??
(doesn't work on NT)
|
|
|
|
|
I have an application with a single document; I use the doc/view architecture to manage the main views ( 3d views ), and I have a couple of other "views" ( not CView ) that display some data from the document.
When loading a document, I need to fill the other views ...
I'm not sure exactly where to do this.
I handle the void MyApp::OnFileOpen() to fill in the CFileDialog with a custom filter and extensions list, and call CWinApp::OpenDocumentFile (sPath);
void CBuild_itApp::OnFileOpen()
{
CWinApp::OpenDocumentFile (sPath);
FillInOtherViews();
}
I could add calls to the end of that method to fill in the other views, but it does not look kosher. I can also trigger a notification ( with observers that I already use elsewhere ) to make the other views handle themselves.
Any thoughts ?
Thanks.
Maximilien Lincourt
Your Head A Splode - Strong Bad
|
|
|
|
|
|
I am doing a project on face facial detection and expression analysis
Presently, i have got the coordinates of the faces facial of both the eyes and the mouth
With these pts as output for a neutral expreeion, i can set control values group certain expression as happy or sad. e.g happy is seen by eyes smaller, smile wider.
how do i call these pts out again
|
|
|
|
|
Our application has RC Files for a couple of languages, and the framework loads the appropriate language according to OS version.
Though I would like to choose and change the language at run time.
Any clue?
-MyttO
|
|
|
|
|
Hello!
You may use:
1. LoadLibrary() along with AfxSetInstanceHandle() (for mfc app) on given resource dll (can be resource only but not must be)
2. You may try to use SetThreadLocale() and use only one resource dll with many resources, each defined for every language you may want to support. But SetThreadLocale is not supported under Windows9x
I propose to use 1st method.
|
|
|
|
|
I'm the second case, ie my dlls have resources defined in multiple languages.
I use SetThreadLocal() in InitInstance() with no error but resources are still loaded in OS Version language (working under Win2k)
Did i do something wrong?
-MyttO
|
|
|
|
|
Hello,
Can anyone help me how to load an extension dll explicitly or dynamically?
thanks..
sphynx
|
|
|
|