2016-04-21 13 views
1

Ich habe diesen multiset Behälter gerichtet ist:ein Objekt Cast, die von einem Iterator

multiset<IMidiMsgExt, IMidiMsgExtComp> queuedNotes; 

IMidiMsgExt ist eine Struktur Ich habe mich geschaffen (ich brauche es für eine zusätzliche Eigenschaft, mTick), die IMidiMsg verlängern:

struct IMidiMsgExt : public IMidiMsg 
{ 
    IMidiMsgExt() { 
    } 

    double mTick = 0.; 

    void IMidiMsgExt::MakeNoteOnMsg(int noteNumber, int velocity, int offset, double tick, int channel) 
    { 
     Clear(); 
     mStatus = channel | (kNoteOn << 4); 
     mData1 = noteNumber; 
     mData2 = velocity; 
     mOffset = offset; 
     mTick = tick; 
    } 

    void IMidiMsgExt::MakeNoteOffMsg(int noteNumber, int offset, double tick, int channel) 
    { 
     Clear(); 
     mStatus = channel | (kNoteOff << 4); 
     mData1 = noteNumber; 
     mOffset = offset; 
     mTick = tick; 
    } 

    void IMidiMsgExt::Clear() 
    { 
     mOffset = 0; 
     mStatus = mData1 = mData2 = 0; 
     mTick = 0.; 
    } 
}; 

Next: ich speichere dass queuedNotes multiset einigen IMidiMsgExt Objekte, mit:

IMidiMsgExt* noteOff = new IMidiMsgExt; 
noteOff->MakeNoteOffMsg(57, 0, tickSize * 111, 0); 
queuedNotes.insert(*noteOff); 

Jetzt muss ich eine Funktion namens SendMidiMsg(IMidiMsg* pMsg) (die IMidiMsg Typ als Eingabe verwendet) verwenden, senden Sie mein Objekt zu ihm.

ich extrahiere das erste Objekt aus meiner Liste zu einem Iterator:

auto midiMessage = queuedNotes.begin(); 

Aber wenn ich versuche, es zu werfen und verwenden SendMidiMsg:

SendMidiMsg((IMidiMsgExt*)midiMessage); 

sagt es no suitable conversion function from "std::_Tree_const_iterator<std::_Tree_val<std::_Tree_simple_types<IMidiMsgExt>>>" to "IMidiMsg *" exists

Wo ist Ich falsch? Sollte ich dynamic casting verwenden?

Antwort

4
auto midiMessage = queuedNotes.begin(); 

midiMessage ist vom Typ std::multiset::iterator. Und es ist nicht konvertierbar zu Ihrem Typ . Iterator ist ein Objekt, das sich ähnlich wie ein Zeiger verhält. Sie können also den Dereferenzoperator (*) verwenden, um das Objekt zu erhalten, auf das er "zeigt". Sie müssen das abgeleitete Objekt auch nicht implizit auf seine Basis umwandeln. Alles, was Sie tun müssen, ist die Adresse, wo der Iterator bekommt „Punkte“ einen Zeiger auf IMidiMsgExt zu erhalten:

SendMidiMsg(&*midiMessage); 

Ein schnellen Abbau von &*midiMessage:

variable -  type 
midiMessage - std::multiset::iterator 
*midiMessage - IMidiMsgExt 
&*midiMessage - IMidiMsgExt* 

bearbeiten : Über Ihren Fehler const_iterator. std::multiset::begin() is supposed to always return const_iterator. Ihre Funktion SendMidiMsg() möchte einen nicht konstanten Zeiger - es sagt, es möchte die Nachricht bearbeiten. multiset erlaubt keine Änderung der Elemente.

Sie können die Nachricht kopieren und dann SendMidiMsg() anrufen. Wenn Sie die Nachricht im Container nicht mehr benötigen, können Sie sie auch später löschen.

auto msg = *midiMessage; 
SendMidiMsg(&msg); 
queuedNotes.erase(midiMessage); 

Hinweis: Es scheint, wie Sie ein Speicherleck im Programm haben. Sie erstellen Nachrichten mit neuen und ich sehe keine Anrufe zu löschen, um den Speicher freizugeben.

IMidiMsgExt* noteOff = new IMidiMsgExt; 
noteOff->MakeNoteOffMsg(57, 0, tickSize * 111, 0); 
queuedNotes.insert(*noteOff); 
+0

Aber es sagt: 'Argument vom Typ "const IMidiMsgExt *" mit dem Parameter des Typs "IMidiMsg *" unvereinbar ist' – markzzz

+0

@paizza Das mess, dass 'queuedNotes.begin()' gibt einen 'const_iterator'. Wenn Sie einen 'const_iterator' dereferenzieren, wird eine konstante Referenz auf das Objekt zurückgegeben.Ihre 'SendMidiMsg()' erwartet einen nicht konstanten Zeiger. Sie haben einen konzeptionellen Fehler in Ihrem Programm. Sie versuchen, etwas zu ändern, das Sie nicht ändern sollten. – rozina

+0

Ich kann 'SendMidiMsg()' nicht ändern, da es eine Methode innerhalb des Frameworks ist, das ich verwenden werde. Die einzige Möglichkeit besteht darin, den zurückkehrenden Typ "iterator" zu ändern. Aber auch dort: Ich kann die Multiset-Liste nicht bearbeiten. Muss ich den Behälter wechseln? Etwas, das ein nicht-konstantes Element speichert und zurückgibt? – markzzz

Verwandte Themen