Sdílet prostřednictvím


Chyba kompilátoru C2440

„conversion“: nelze převést z „type1“ nebo „type2“.

Kompilátor nelze převést z 'type1' do 'type2".

Příklad

C2440 může být způsobena, pokud se pokusíte inicializovat nekonstantní char* (nebo wchar_t*) pomocí řetězce literálu v kódu jazyka C++, když možnost přizpůsobení kompilátoru /Zc:strictStrings je nastavena.V jazyku C je typ řetězcového literálu pole char, ale v jazyce C++ je pole constchar.Tato ukázka generuje C2440:

// C2440s.cpp
// Build: cl /Zc:strictStrings /W3 C2440s.cpp
// When built, the compiler emits:
// error C2440: 'initializing' : cannot convert from 'const char [5]' 
// to 'char *'
//        Conversion from string literal loses const qualifier (see
// /Zc:strictStrings)

int main() {
   char* s1 = "test"; // C2440
   const char* s2 = "tests"; // OK
}

C2440 může vzniknout také při pokusu o převod ukazatele na člen na void*.Následující ukázka generuje upozornění C2440:

// C2440.cpp
class B {
public:
   void  f(){;}

   typedef void (B::*pf)();

   void f2(pf pf) {
       (this->*pf)();
       void* pp = (void*)pf;   // C2440
   }

   void f3() {
      f2(f);
   }
};

C2440 může také zapříčinit, pokud jste se pokusili přetypovat z typu, který je deklarován pouze vpřed, ale není definován.Tato ukázka generuje C2440:

// c2440a.cpp 
struct Base { }; // Defined

struct Derived; // Forward declaration, not defined

Base * func(Derived * d) {
    return static_cast<Base *>(d); // error C2440: 'static_cast' : cannot convert from 'Derived *' to 'Base *'
}

Chyby C2440 v řádcích 15 a 16 další ukázky jsou kvalifikované ve zprávách Incompatible calling conventions for UDT return value. (UDT je typ definovaný uživatelem, například třída, struktura nebo sjednocení.) Tyto druhy chyb nekompatibility jsou způsobeny, když je konvence volání UDT definovaná uživatelem v návratovém typu dopředné deklarace je v konfliktu se skutečnou konvencí volání UDT a když je zahrnutý ukazatel na funkci.

V příkladu jsou nejprve dopředné deklarace pro strukturu a funkci, která vrátí strukturu; kompilátor předpokládá, že struktura používá konvenci volání jazyka C++.Dále je definice struktury, která standardně používá konvence volání C.Vzhledem k tomu, že kompilátor nezná konvence volání dané struktury, dokud nedokončí čtení celé struktury, konvence volání pro strukturu v návratovém typu get_c2 se také považuje za C++.

Struktura je následována jinou deklarací funkce, která vrací strukturu, ale v tomto okamžiku kompilátor ví, že je konvence volání struktury C++.Podobně ukazatel funkce, který vrátí strukturu, je definován po definici struktury, takže kompilátor ví, že struktura používá konvence volání C++.

Chcete-li vyřešit chybu C2440, která nastává z důvodu nekompatibilních konvencí volání, deklarujte funkce vracející typ definovaný uživatelem po definici UDT.

// C2440b.cpp
struct MyStruct;

MyStruct get_c1();

struct MyStruct {
   int i;
   static MyStruct get_C2();
};

MyStruct get_C3();

typedef MyStruct (*FC)();

FC fc1 = &get_c1;   // C2440, line 15
FC fc2 = &MyStruct::get_C2;   // C2440, line 16
FC fc3 = &get_C3;

class CMyClass {
public:
   explicit CMyClass( int iBar)
      throw()   {
   }

   static CMyClass get_c2();
};

int main() {
   CMyClass myclass = 2;   // C2440
   // try one of the following
   // CMyClass myclass{2};
   // CMyClass myclass(2);

   int *i;
   float j;
   j = (float)i;   // C2440, cannot cast from pointer to int to float
}

C2440 může vzniknout také v případě, že přiřadíte nulový vnitřní ukazatel:

// C2440c.cpp
// compile with: /clr
int main() {
   array<int>^ arr = gcnew array<int>(100);
   interior_ptr<int> ipi = &arr[0];
   ipi = 0;   // C2440
   ipi = nullptr;   // OK
}

C2440 může vzniknout také kvůli nesprávnému použití uživatelem definovaného převodu.Další informace o uživatelem definovaných převodech viz Uživatelem definované převody).Tato ukázka generuje C2440:

// C2440d.cpp
// compile with: /clr
value struct MyDouble {
   double d;
   // convert MyDouble to Int32
   static explicit operator System::Int32 ( MyDouble val ) {
      return (int)val.d;
   }
};

int main() {
   MyDouble d;
   int i;
   i = d;   // C2440
   // Uncomment the following line to resolve.
   // i = static_cast<int>(d);
}

C2440 může vzniknout také při pokusu o vytvoření instance pole Visual C++, jehož typ je Array. Další informace naleznete v tématu Pole (rozšíření komponent C++). Následující ukázka generuje upozornění C2440:

// C2440e.cpp
// compile with: /clr
using namespace System;
int main() {
   array<int>^ intArray = Array::CreateInstance(__typeof(int), 1);   // C2440
   // try the following line instead
   // array<int>^ intArray = safe_cast<array<int> ^>(Array::CreateInstance(__typeof(int), 1));
}

C2440 může vzniknout také z důvodu změn ve funkci atributů. Následující ukázka generuje upozornění C2440.

// c2440f.cpp
// compile with: /LD
[ module(name="PropDemoLib", version=1.0) ];   // C2440
// try the following line instead
// [ module(name="PropDemoLib", version="1.0") ];

Kompilátor Visual C++ již neumožňuje const_cast – operátor pro přetypování směrem dolů, když je sestaven zdrojový kód, který používá programování /clr.

Chcete-li vyřešit tuto chybu C2440, použijte správný operátor osazení.Další informace naleznete v tématu Operátory přetypování.

Tato ukázka generuje C2440:

// c2440g.cpp
// compile with: /clr
ref class Base {};
ref class Derived : public Base {};
int main() {
   Derived ^d = gcnew Derived;
   Base ^b = d;
   d = const_cast<Derived^>(b);   // C2440
   d = dynamic_cast<Derived^>(b);   // OK
}

C2440 může být také generovány pomocí /clr:oldSyntax:

// c2440h.cpp
// compile with: /clr:oldSyntax
__gc class Base {};
__gc class Derived : public Base {};
int main() {
   Derived *d = new Derived;
   Base *b = d;
   d = const_cast<Derived*>(b);   // C2440
   d = dynamic_cast<Derived*>(b);   // OK
}