Visualizzazione dei risultati da 1 a 10 su 10
  1. #1
    Utente di HTML.it
    Registrato dal
    Jun 2003
    Messaggi
    4,826

    [c++]errori linker

    ciao.

    ho questa classe tuple:

    .h
    [code]
    #pragma once

    template<typename TYPE, int SIZE> class CVar
    {
    public:
    CVar(void){};
    ~CVar(void){};
    bool operator ==(const CVar& var)const;
    bool operator != (const CVar& var)const;
    void operator =(const CVar& var)const;
    bool operator >(const CVar& var)const;
    bool operator <(const CVar& var)const;
    bool operator >=(const CVar& var)const;
    bool operator <=(const CVar& var)const;
    TYPE mVar[SIZE];

    };
    [code]

    e cpp:
    codice:
    #include "StdAfx.h"
    #include "Var.h"
    //
    
    template<typename TYPE, int SIZE>
    bool CVar<TYPE, SIZE>::operator== (const CVar&)const
    {
    	return memcmp(mVar, CVar.mVar, SIZE*sizeof(TYPE)) == 0;
    }
    
    template<typename TYPE, int SIZE>
    bool CVar<TYPE, SIZE>::operator!= (const CVar&)const
    {
    	return memcmp(mVar, CVar.mVar, SIZE*sizeof(TYPE)) != 0;
    }
    
    template<typename TYPE, int SIZE>
    bool CVar<TYPE, SIZE>::operator> (const CVar&)const
    {
    	return memcmp(mVar, CVar.mVar, SIZE*sizeof(TYPE)) > 0;
    }
    
    
    template<typename TYPE, int SIZE>
    bool CVar<TYPE, SIZE>::operator< (const CVar&)const
    {
    	return memcmp(mVar, CVar.mVar, SIZE*sizeof(TYPE)) < 0;
    }
    
    
    template<typename TYPE, int SIZE>
    bool CVar<TYPE, SIZE>::operator>= (const CVar&)const
    {
    	return memcmp(mVar, CVar.mVar, SIZE*sizeof(TYPE)) >= 0;
    }
    
    template<typename TYPE, int SIZE>
    bool CVar<TYPE, SIZE>::operator<= (const CVar&)const
    {
    	return memcmp(mVar, CVar.mVar, SIZE*sizeof(TYPE)) <= 0;
    }
    
    template<typename TYPE, int SIZE>
    void CVar<TYPE, SIZE>::operator= (const CVar&)const
    {
    	memcpy((void*)mVar.mVar, (void*)CVar.mVar, SIZE*sizeof(TYPE));
    
    }
    eredito per creare un float4:
    .h
    codice:
    #pragma once
    #include "Var.h"
    
    class Float4 : public CVar<float, 4>
    {
    public:
    	Float4(void);
    	Float4(float f1, float f2, float f3, float f4);
    	Float4 (const Float4& var);
    	void SetValue(float f1, float f2, float f3, float f4);
    	~Float4(void);
    };
    e
    cpp
    codice:
    #include "StdAfx.h"
    #include "Float4.h"
    
    Float4::Float4(void)
    {
    }
    
    Float4::Float4(float f1, float f2 ,float f3 , float f4)
    {
    	mVar[0] = f1;
    	mVar[1] = f2;
    	mVar[2] = f3;
    	mVar[3] = f4;
    }
    
    Float4::Float4 (const Float4& var)
    {
    	mVar[0] = var.mVar[0];
    	mVar[1] = var.mVar[1];
    	mVar[2] = var.mVar[2];
    	mVar[3] = var.mVar[3];
    }
    
    Float4::~Float4(void)
    {
    }
    
    void Float4::SetValue(float f1, float f2, float f3, float f4)
    {
    	mVar[0] = f1;
    	mVar[1] = f2;
    	mVar[2] = f3;
    	mVar[3] = f4;
    }

    se la compilo nel progetto in cui è una dll c++ non da nessun errore e cosi' se le includo in altre librerie statiche .lib o dll.
    Il problema è che quando le inserisco in un progetto che è un applicazione win32 il linker mi da questi errori:
    1>Linking...
    1>Application.obj : warning LNK4075: ignoring '/EDITANDCONTINUE' due to '/OPT:ICF' specification
    1>WinApplication.obj : error LNK2019: unresolved external symbol "public: __thiscall Float4::~Float4(void)" (??1Float4@@QAE@XZ) referenced in function "public: __thiscall PGE::CWinApplication::CWinApplication(int,int,int, int,class std::basic_string<wchar_t,struct std::char_traits<wchar_t>,class std::allocator<wchar_t> >,class Float4)" (??0CWinApplication@PGE@@QAE@HHHHV?$basic_string@_ WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@VF loat4@@@Z)
    1>WindowApplication.obj : error LNK2001: unresolved external symbol "public: __thiscall Float4::~Float4(void)" (??1Float4@@QAE@XZ)
    1>WinApplication.obj : error LNK2019: unresolved external symbol "public: __thiscall Float4::Float4(class Float4 const &)" (??0Float4@@QAE@ABV0@@Z) referenced in function "public: __thiscall PGE::CWinApplication::CWinApplication(int,int,int, int,class std::basic_string<wchar_t,struct std::char_traits<wchar_t>,class std::allocator<wchar_t> >,class Float4)" (??0CWinApplication@PGE@@QAE@HHHHV?$basic_string@_ WU?$char_traits@_W@std@@V?$allocator@_W@2@@std@@VF loat4@@@Z)
    1>WindowApplication.obj : error LNK2001: unresolved external symbol "public: __thiscall Float4::Float4(class Float4 const &)" (??0Float4@@QAE@ABV0@@Z)
    1>WinApplication.obj : error LNK2019: unresolved external symbol "public: __thiscall Float4::Float4(void)" (??0Float4@@QAE@XZ) referenced in function "public: __thiscall PGE::CWindowApplication::CWindowApplication(void)" (??0CWindowApplication@PGE@@QAE@XZ)
    1>WindowApplication.obj : error LNK2019: unresolved external symbol _D3D11CreateDeviceAndSwapChain@48 referenced in function "public: long __thiscall PGE::CWindowApplication::InitDevice(void)" (?InitDevice@CWindowApplication@PGE@@QAEJXZ)
    1>C:\PGN\trunk\PGE\Debug\PGEApplication.exe : fatal error LNK1120: 4 unresolved externals
    1>Build log was saved at "file://c:\PGN\trunk\PGEApplication\Debug\BuildLog.htm"
    1>PGEApplication - 7 error(s), 1 warning(s)
    ========== Build: 0 succeeded, 1 failed, 0 up-to-date, 0 skipped ==========


    premetto che ho cercato a lungo una soluzione.
    grazie.


    ps. devo trovare soluzione solo agli errori del linker per i float4 , gli altri errori li ho messi a posto.

  2. #2
    Utente di HTML.it
    Registrato dal
    Jun 2003
    Messaggi
    4,826
    dimenticavo , questo è il costruttore dove dovrebbe essere l'errore:

    codice:
    CWinApplication::CWinApplication(const int nWidth,const int nHeight, const int nXPosition, const int nYPosition, 
    								 wstring strWindowsTitle, Float4 fClearColor):
    CWindowApplication(nWidth, nHeight, nXPosition, nYPosition, strWindowsTitle, fClearColor){}
    e anche questo , l'header
    
    CWinApplication();
    	CWinApplication(const int nWidth,const int nHeight, const int nXPosition, const int nYPosition, 
    		wstring strWindowsTitle, Float4 fClearColor) ;
    	~CWinApplication();

  3. #3
    Utente di HTML.it L'avatar di shodan
    Registrato dal
    Jun 2001
    Messaggi
    2,381
    Le funzioni template non puoi metterle in un .cpp senza espliticitare i parametri template.
    (E già hai avuto un problema simile tempo fa.)
    E che compilatore usi?
    This code and information is provided "as is" without warranty of any kind, either expressed
    or implied, including but not limited to the implied warranties of merchantability and/or
    fitness for a particular purpose.

  4. #4
    Utente di HTML.it
    Registrato dal
    Jun 2003
    Messaggi
    4,826
    uso vs 2008 , cosa vuol dire?
    scusa se te lo chiedo ancora.
    ciao.
    grazie.

  5. #5
    Utente di HTML.it L'avatar di shodan
    Registrato dal
    Jun 2001
    Messaggi
    2,381
    Chiedevo perché quella classe mi ricorda parecchio std::array<> fornito con VC++ 2010 o boost::array<> per cui potevi fare semplicemente (tralasciando il namespace per chiarezza):

    codice:
        typedef array<float,4> Float4;
    
        Float4 f4a = { 1.0,2.3, 4.7,5.57};
        Float4 f4b = { 13.01,2.7, 2.7,4.7};
    
        cout << ( f4a == f4b ) << endl;
        // etc.
    In ogni caso non è quello il tuo problema, ma aver messo la definizione delle funzioni in un file .cpp invece che nel file header (e senza lo specificatore inline).

    Per inciso: se vuoi mantenere le funzioni in un file cpp è possibile ma solo se espliciti i parametri.
    codice:
    template<>
    bool CVar<float, 4>::operator== (const CVar& rhs) 
    {
    	return memcmp(mVar, CVar.mVar, 4*sizeof(float)) == 0;
    }
    però se cambi il tipo o la dimensione sei fregato.
    This code and information is provided "as is" without warranty of any kind, either expressed
    or implied, including but not limited to the implied warranties of merchantability and/or
    fitness for a particular purpose.

  6. #6
    Utente di HTML.it
    Registrato dal
    Jun 2003
    Messaggi
    4,826
    grassie

  7. #7
    Utente di HTML.it
    Registrato dal
    Jun 2003
    Messaggi
    4,826
    ho ritrovato l'esempio , shodan pero ' è cosi :

    .inl
    codice:
    //----------------------------------------------------------------------------
    template <int DIMENSION, typename TYPE>
    Tuple<DIMENSION,TYPE>::Tuple ()
    {
        // Uninitialized for native data.  Initialized for class data as long as
        // TYPE's default constructor initializes its own data.
    }
    //----------------------------------------------------------------------------
    template <int DIMENSION, typename TYPE>
    Tuple<DIMENSION,TYPE>::Tuple (const Tuple& tuple)
    {
        for (int i = 0; i < DIMENSION; ++i)
        {
            mTuple[i] = tuple.mTuple[i];
        }
    }
    //----------------------------------------------------------------------------
    template <int DIMENSION, typename TYPE>
    Tuple<DIMENSION,TYPE>::~Tuple ()
    {
    }
    //----------------------------------------------------------------------------
    template <int DIMENSION, typename TYPE>
    inline Tuple<DIMENSION,TYPE>::operator const TYPE* () const
    {
        return mTuple;
    }
    //----------------------------------------------------------------------------
    template <int DIMENSION, typename TYPE>
    inline Tuple<DIMENSION,TYPE>::operator TYPE* ()
    {
        return mTuple;
    }
    //----------------------------------------------------------------------------
    template <int DIMENSION, typename TYPE>
    inline TYPE Tuple<DIMENSION,TYPE>::operator[] (int i) const
    {
        return mTuple[i];
    }
    //----------------------------------------------------------------------------
    template <int DIMENSION, typename TYPE>
    inline TYPE& Tuple<DIMENSION,TYPE>::operator[] (int i)
    {
        return mTuple[i];
    }
    //----------------------------------------------------------------------------
    template <int DIMENSION, typename TYPE>
    Tuple<DIMENSION,TYPE>& Tuple<DIMENSION,TYPE>::operator= (const Tuple& tuple)
    {
        for (int i = 0; i < DIMENSION; ++i)
        {
            mTuple[i] = tuple.mTuple[i];
        }
        return *this;
    }
    //----------------------------------------------------------------------------
    template <int DIMENSION, typename TYPE>
    bool Tuple<DIMENSION,TYPE>::operator== (const Tuple& tuple) const
    {
        return memcmp(mTuple, tuple.mTuple, DIMENSION*sizeof(TYPE)) == 0;
    }
    //----------------------------------------------------------------------------
    template <int DIMENSION, typename TYPE>
    bool Tuple<DIMENSION,TYPE>::operator!= (const Tuple& tuple) const
    {
        return memcmp(mTuple, tuple.mTuple, DIMENSION*sizeof(TYPE)) != 0;
    }
    //----------------------------------------------------------------------------
    template <int DIMENSION, typename TYPE>
    bool Tuple<DIMENSION,TYPE>::operator< (const Tuple& tuple) const
    {
        return memcmp(mTuple, tuple.mTuple, DIMENSION*sizeof(TYPE)) < 0;
    }
    //----------------------------------------------------------------------------
    template <int DIMENSION, typename TYPE>
    bool Tuple<DIMENSION,TYPE>::operator<= (const Tuple& tuple) const
    {
        return memcmp(mTuple, tuple.mTuple, DIMENSION*sizeof(TYPE)) <= 0;
    }
    //----------------------------------------------------------------------------
    template <int DIMENSION, typename TYPE>
    bool Tuple<DIMENSION,TYPE>::operator> (const Tuple& tuple) const
    {
        return memcmp(mTuple, tuple.mTuple, DIMENSION*sizeof(TYPE)) > 0;
    }
    //----------------------------------------------------------------------------
    template <int DIMENSION, typename TYPE>
    bool Tuple<DIMENSION,TYPE>::operator>= (const Tuple& tuple) const
    {
        return memcmp(mTuple, tuple.mTuple, DIMENSION*sizeof(TYPE)) >= 0;
    }
    //----------------------------------------------------------------------------

    .h

    codice:
    // Geometric Tools, LLC
    // Copyright (c) 1998-2010
    // Distributed under the Boost Software License, Version 1.0.
    // http://www.boost.org/LICENSE_1_0.txt
    // http://www.geometrictools.com/Licens...ICENSE_1_0.txt
    //
    // File Version: 5.0.1 (2010/04/14)
    
    #ifndef WM5TUPLE_H
    #define WM5TUPLE_H
    
    #include "Wm5CoreLIB.h"
    
    // The class TYPE is either native data or is class data that has the
    // following member functions:
    //   TYPE::TYPE ()
    //   TYPE::TYPE (const TYPE&);
    //   TYPE& TYPE::operator= (const TYPE&)
    
    namespace Wm5
    {
    
    template <int DIMENSION, typename TYPE>
    class Tuple
    {
    public:
        // Construction and destruction.  The default constructor does not
        // initialize the tuple elements for native elements.  The tuple elements
        // are initialized for class data whenever TYPE initializes during its
        // default construction.
        Tuple ();
        Tuple (const Tuple& tuple);
        ~Tuple ();
    
        // Coordinate access.
        inline operator const TYPE* () const;
        inline operator TYPE* ();
        inline TYPE operator[] (int i) const;
        inline TYPE& operator[] (int i);
    
        // Assignment.
        Tuple& operator= (const Tuple& tuple);
    
        // Comparison.  The inequalities make the comparisons using memcmp, thus
        // treating the tuple as an array of unsigned bytes.
        bool operator== (const Tuple& tuple) const;
        bool operator!= (const Tuple& tuple) const;
        bool operator<  (const Tuple& tuple) const;
        bool operator<= (const Tuple& tuple) const;
        bool operator>  (const Tuple& tuple) const;
        bool operator>= (const Tuple& tuple) const;
    
    protected:
        TYPE mTuple[DIMENSION];
    };
    
    #include "Wm5Tuple.inl"
    
    }
    
    #endif

    come funziona questo esempio?
    il problema è che ci sono vari modi da quel che ho capito e ne dovro scegliere uno solo per programmare con i template.
    Perchè l'inline è sempre presente coi template?
    Mitaly mi ha spiegato a grandi linee cosa fa , ma sono un po incerto.
    Sono alle prime armi con i template.

  8. #8
    Utente di HTML.it
    Registrato dal
    Jun 2003
    Messaggi
    4,826
    In pratica nell esempio che ho postato include un file .inl in modo che sia un espansione della classe .h in cui è incluso il template , mi sembra un buon metodo, o no?

    quello che non ho capito principalmente non sono le funzioni inline , bensi perchè vengono usate nei template ( o è opzionale utilizzarle con i template).
    Da quello che sto leggendo anche il template esegue più o meno la stessa cosa delle funzioni inline, l' espansione del codice fatta dal compilatore , mi chiedevo se le due cose(inline e template) fossero relazionate.

    L'ultima cosa: i costruttori nei template, si utilizza un modo diverso per dichiararli e implementarli?

    grazie

  9. #9
    Utente di HTML.it L'avatar di shodan
    Registrato dal
    Jun 2001
    Messaggi
    2,381
    Originariamente inviato da giuseppe500
    In pratica nell esempio che ho postato include un file .inl in modo che sia un espansione della classe .h in cui è incluso il template , mi sembra un buon metodo, o no?
    Più che un'espansione è l'unico modo per tenere distinta interfaccia e funzioni. Nulla vieta di usare un unico file (per cose piccole non è un grosso problema).

    quello che non ho capito principalmente non sono le funzioni inline , bensi perchè vengono usate nei template ( o è opzionale utilizzarle con i template).
    No. Non è opzionale.
    Da quello che sto leggendo anche il template esegue più o meno la stessa cosa delle funzioni inline, l' espansione del codice fatta dal compilatore , mi chiedevo se le due cose(inline e template) fossero relazionate.
    Il fatto che una funzione sia un template rende obbligatorio che sia inline
    La regola è: tutte le funzioni dichiarate e definite in un file header, o file incluso da un file header visibile ad altre unità di compilazione, devono avere la parola chiave inline.
    L'ultima cosa: i costruttori nei template, si utilizza un modo diverso per dichiararli e implementarli?
    No. La sola differenza rispetto a un funzione template è che il costruttore è chiamato in automatico quando viene costruito un oggetto.
    This code and information is provided "as is" without warranty of any kind, either expressed
    or implied, including but not limited to the implied warranties of merchantability and/or
    fitness for a particular purpose.

  10. #10

Permessi di invio

  • Non puoi inserire discussioni
  • Non puoi inserire repliche
  • Non puoi inserire allegati
  • Non puoi modificare i tuoi messaggi
  •  
Powered by vBulletin® Version 4.2.1
Copyright © 2024 vBulletin Solutions, Inc. All rights reserved.