Domanda

Ho alcuni difetti di segmentazione intermittenti in un'applicazione Qt. Credo che il problema è legato alla nostra (cattivo) uso di QSharedPointer. Il Qt documentazione afferma :

  

QSharedPointer :: QSharedPointer (T * PTR):   Crea un QSharedPointer che punti PTR. Il PTR puntatore viene gestito da questo QSharedPointer e non deve essere passato a un altro oggetto QSharedPointer o cancellato fuori questo oggetto .

Credo che stiamo facendo sia non deve ...: /

C'è un modo per far rispettare OOP che il puntatore gestito da QSharedPointer non può essere eliminato o passata ad un altro QSharedPointer?

La soluzione migliore sarà quello di avere un errore di compilazione.

È stato utile?

Soluzione

Il modello normale è quello di mettere la dichiarazione new all'interno costruttore della puntatore intelligente, in questo modo:

QSharedPointer<Obj> p (new Obj(2)); 

In questo modo non hanno mai un riferimento al puntatore nudo in sé.

Se refactoring del codice in modo che tutti i nuovi operatori sono in righe come queste, tutti i vostri problemi saranno risolti.

Altri suggerimenti

Bene, un modo OOP-esque sarebbe quella di creare il puntatore crudo come un membro privato in una classe wrapper, e solo eseguire azioni sul puntatore attraverso metodi che agiscono sul puntatore condiviso. tipo di sciocco, però, non è vero?

In alternativa si potrebbe fare la classe con il puntatore del grezzo di una classe base alle vostre altre classi e rendere il puntatore grezzo un membro privato nella classe. A questo proposito, si è più o meno la creazione di una classe astratta che non fa nulla. Le tue lezioni derivati ??devono invece fare tutto il lavoro, e dal momento che non possono accedere al puntatore grezzo, la compilazione fallirà ... questo non fa qualcuno non stop da solo copiare il valore del puntatore grezzo fuori del puntatore condiviso, però.

Alla fine, credo che la vostra politica migliore è quella di manuall cambiare tutte le funzioni in questione ad uso sia un puntatore condiviso oppure un puntatore crudo. È possibile copiare un puntatore condiviso ad un altro in modo sicuro, quindi perché non basta andare in quel modo?

Modifica: Potrei aggiungere che, indipendentemente dal fatto che si sta utilizzando puntatori condivisi, suona come hai questioni legate alla proprietà. Se un puntatore è stato creato in un ambito, dovrebbe essere eliminato in tale ambito, a meno che la funzione che esso è passato a contrattualmente assume la proprietà del puntatore. Utilizzando un puntatore condiviso in questo scenario sarà causato solo insetti differenti, alla fine. Sembra che avete problemi di progettazione più profondo che solo la condivisione dei puntatori.

Non ho dimestichezza con la particolare implementazione Qt di un puntatore condiviso, ma come linea guida generale: il tentativo di mescolare i puntatori prime con puntatori gestiti di solito finisce nel sangue. Una volta che si 'fiducia' un'implementazione puntatore condiviso nel prendere la proprietà dei dati allocati dinamicamente, si dovrebbe in nessun caso cercare di gestire la durata degli oggetti stessi (ad esempio eliminando il puntatore fornito).

C'è un modo per far rispettare OOP che il puntatore gestito da QSharedPointer non può essere eliminato?

Credo che si potrebbe immaginare una certa tecnica strana in cui il tipo di punta avrebbe un distruttore privato e dichiarare QSharedPointer come amico (che impedirebbe efficacemente qualsiasi 'eliminazione di fuori' da compilare), ma io non ci scommetterei che tutto ciò che di buono può venire fuori da questo (e si noti che renderà il vostro tipo assolutamente inutilizzabile a meno che new'ed e trasferito ad un QSharedPointer).

C'è un modo per far rispettare OOP che il puntatore gestito da QSharedPointer non può essere passato ad un altro QSharedPointer?

Non riesco a pensare di qualsiasi, e questo è un altro motivo per cui si dovrebbe evitare di manipolare il puntatore grezzo, una volta di proprietà è stata trasferita ad un QSharedPointer.

Controlla il tuo codice per tutti gli usi .data () e verificare quello che ritornano non è né memorizzato ne cancellato. Non credo che un errore di compilazione difficile sarebbe buono, perché a volte va bene per passare il puntatore cruda, per esempio a una funzione che non memorizza né cancellare puntatori passati. (Specialmente quando si utilizza il codice 3rd-party, non si può sempre cambiare tutto per utilizzare i puntatori condivisi, e spesso si desidera lavorare con entrambi, PTR prime e condivisi). Si potrebbe segnare QSharedPointer :: dati () come deprecato (da patch Qt), per ottenere un avvertimento momento della compilazione.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top