Ottimizzazione di persistenza e inizializzazione

Per impostazione predefinita, la persistenza e l'inizializzazione in un controllo vengono gestite dalla DoPropExchange funzione membro. In un controllo tipico questa funzione contiene chiamate a diverse funzioni PX_ (PX_Color, PX_Fonte così via), una per ogni proprietà.

Questo approccio offre il vantaggio che una singola DoPropExchange implementazione può essere usata per l'inizializzazione, per la persistenza in formato binario e per la persistenza nel formato cosiddetto "property-bag" usato da alcuni contenitori. Questa funzione fornisce tutte le informazioni sulle proprietà e i relativi valori predefiniti in un'unica posizione comoda.

Tuttavia, questa generalità è a scapito dell'efficienza. Le funzioni PX_ ottengono la loro flessibilità tramite implementazioni multilivello che sono intrinsecamente meno efficienti rispetto ad approcci più diretti, ma meno flessibili. Inoltre, se un controllo passa un valore predefinito a una funzione PX_ , tale valore predefinito deve essere fornito ogni volta, anche in situazioni in cui il valore predefinito potrebbe non essere necessariamente utilizzato. Se la generazione del valore predefinito è un'attività nontriva (ad esempio, quando il valore viene ottenuto da una proprietà di ambiente), vengono eseguite operazioni aggiuntive e non necessarie nei casi in cui il valore predefinito non viene usato.

È possibile migliorare le prestazioni di persistenza binaria del controllo eseguendo l'override della funzione del Serialize controllo. L'implementazione predefinita di questa funzione membro effettua una chiamata alla DoPropExchange funzione. Eseguendo l'override, è possibile fornire un'implementazione più diretta per la persistenza binaria. Si consideri ad esempio questa DoPropExchange funzione:

void CMyAxOptCtrl::DoPropExchange(CPropExchange* pPX)
{
   ExchangeVersion(pPX, MAKELONG(_wVerMinor, _wVerMajor));
   COleControl::DoPropExchange(pPX);

   PX_Bool(pPX, _T("BoolProp"), m_BoolProp, TRUE);
   PX_Short(pPX, _T("ShortProp"), m_ShortProp, 0);
   PX_Color(pPX, _T("ColorProp"), m_ColorProp, RGB(0xFF, 0x00, 0x00));
   PX_String(pPX, _T("StringProp"), m_StringProp, _T(""));
}

Per migliorare le prestazioni della persistenza binaria di questo controllo, è possibile eseguire l'override della Serialize funzione come indicato di seguito:

void CMyAxOptCtrl::Serialize(CArchive& ar)
{
   SerializeVersion(ar, MAKELONG(_wVerMinor, _wVerMajor));
   SerializeExtent(ar);
   SerializeStockProps(ar);

   if (ar.IsLoading())
   {
      ar >> m_BoolProp;
      ar >> m_ShortProp;
      ar >> m_ColorProp;
      ar >> m_StringProp;
   }
   else
   {
      ar << m_BoolProp;
      ar << m_ShortProp;
      ar << m_ColorProp;
      ar << m_StringProp;
   }
}

La dwVersion variabile locale può essere usata per rilevare la versione dello stato permanente del controllo caricato o salvato. È possibile usare questa variabile anziché chiamare CPropExchange::GetVersion.

Per risparmiare poco spazio nel formato permanente per una proprietà BOOL (e per mantenerlo compatibile con il formato prodotto da PX_Bool), è possibile archiviare la proprietà come BYTE, come indicato di seguito:

if (ar.IsLoading())
{
   BYTE bTmp;
   ar >> bTmp;
   m_BoolProp = (BOOL)bTmp;
   // other properties...
}
else
{
   ar << (BYTE)m_BoolProp;
   // other properties...
}

Si noti che nel caso di caricamento viene usata una variabile temporanea e quindi viene assegnato il relativo valore, anziché eseguire il cast m_boolProp a un riferimento BYTE. La tecnica di cast comporterà la modifica di un solo byte di m_boolProp , lasciando i byte rimanenti non inizializzati.

Per lo stesso controllo, è possibile ottimizzare l'inizializzazione del controllo eseguendo l'override di COleControl::OnResetState come indicato di seguito:

void CMyAxOptCtrl::OnResetState()
{
   ResetVersion(MAKELONG(_wVerMinor, _wVerMajor));
   ResetStockProps();

   m_BoolProp = TRUE;
   m_ShortProp = 0;
   m_ColorProp = RGB(0xFF, 0x00, 0x00);
   m_StringProp.Empty();
}

Anche se Serialize e OnResetState sono stati sottoposti a override, la DoPropExchange funzione deve essere mantenuta intatta perché viene ancora usata per la persistenza nel formato contenitore delle proprietà. È importante mantenere tutte e tre queste funzioni per garantire che il controllo gestisca le relative proprietà in modo coerente, indipendentemente dal meccanismo di persistenza usato dal contenitore.

Vedi anche

Controlli ActiveX MFC: ottimizzazione