Bagikan melalui


com::p tr Class

Pembungkus untuk objek COM yang dapat digunakan sebagai anggota kelas CLR. Pembungkus juga mengotomatiskan manajemen seumur hidup objek COM, melepaskan semua referensi yang dimiliki pada objek ketika destruktornya dipanggil. Analog dengan kelas CComPtr.

Sintaks

template<class _interface_type>
ref class ptr;

Parameter

_interface_type
Antarmuka COM.

Keterangan

Juga com::ptr dapat digunakan sebagai variabel fungsi lokal untuk menyederhanakan berbagai tugas COM dan untuk mengotomatiskan manajemen masa pakai.

com::ptr Tidak dapat digunakan secara langsung sebagai parameter fungsi; gunakan operator referensi Pelacakan atau operator Handle to object (^) sebagai gantinya.

com::ptr Tidak dapat langsung dikembalikan dari fungsi; gunakan handel sebagai gantinya.

Contoh

Contoh ini mengimplementasikan kelas CLR yang menggunakan untuk membungkus com::ptr objek anggota IXMLDOMDocument privatnya. Memanggil metode publik kelas menghasilkan panggilan ke objek yang terkandung IXMLDOMDocument . Sampel membuat instans dokumen XML, mengisinya dengan beberapa XML sederhana, dan melakukan panduan simpul yang disederhanakan di pohon dokumen yang diurai untuk mencetak XML ke konsol.

// comptr.cpp
// compile with: /clr /link msxml2.lib
#include <msxml2.h>
#include <msclr\com\ptr.h>

#import <msxml3.dll> raw_interfaces_only

using namespace System;
using namespace System::Runtime::InteropServices;
using namespace msclr;

// a ref class that uses a com::ptr to contain an
// IXMLDOMDocument object
ref class XmlDocument {
public:
   // construct the internal com::ptr with a null interface
   // and use CreateInstance to fill it
   XmlDocument(String^ progid) {
      m_ptrDoc.CreateInstance(progid);
   }

   void LoadXml(String^ xml) {
      pin_ptr<const wchar_t> pinnedXml = PtrToStringChars(xml);
      BSTR bstr = NULL;

      try {
         // load some XML into the document
         bstr = ::SysAllocString(pinnedXml);
         if (NULL == bstr) {
            throw gcnew OutOfMemoryException;
         }
         VARIANT_BOOL bIsSuccessful = false;
         // use operator -> to call IXMODOMDocument member function
         Marshal::ThrowExceptionForHR(m_ptrDoc->loadXML(bstr, &bIsSuccessful));
      }
      finally {
         ::SysFreeString(bstr);
      }
   }

   // simplified function to write just the first xml node to the console
   void WriteXml() {
      IXMLDOMNode* pNode = NULL;

      try {
         // the first child of the document is the first real xml node
         Marshal::ThrowExceptionForHR(m_ptrDoc->get_firstChild(&pNode));
         if (NULL != pNode) {
            WriteNode(pNode);
         }
      }
      finally {
         if (NULL != pNode) {
            pNode->Release();
         }
      }
   }

   // note that the destructor will call the com::ptr destructor
   // and automatically release the reference to the COM object

private:
   // simplified function that only writes the node
   void WriteNode(IXMLDOMNode* pNode) {
      BSTR bstr = NULL;

      try {
         // write out the name and text properties
         Marshal::ThrowExceptionForHR(pNode->get_nodeName(&bstr));
         String^ strName = gcnew String(bstr);
         Console::Write("<{0}>", strName);
         ::SysFreeString(bstr);
         bstr = NULL;

         Marshal::ThrowExceptionForHR(pNode->get_text(&bstr));
         Console::Write(gcnew String(bstr));
         ::SysFreeString(bstr);
         bstr = NULL;

         Console::WriteLine("</{0}>", strName);
      }
      finally {
         ::SysFreeString(bstr);
      }
   }

   com::ptr<IXMLDOMDocument> m_ptrDoc;
};

// use the ref class to handle an XML DOM Document object
int main() {
   try {
      // create the class from a progid string
      XmlDocument doc("Msxml2.DOMDocument.3.0");

      // stream some xml into the document
      doc.LoadXml("<word>persnickety</word>");

      // write the document to the console
      doc.WriteXml();
   }
   catch (Exception^ e) {
      Console::WriteLine(e);
   }
}
<word>persnickety</word>

Anggota

Konstruktor Publik

Nama Deskripsi
ptr::p tr Membuat untuk membungkus com::ptr objek COM.
ptr::~ptr com::ptrMerusak .

Metode Publik

Nama Deskripsi
ptr::Lampirkan Melampirkan objek COM ke com::ptr.
ptr::CreateInstance Membuat instans objek COM dalam com::ptr.
ptr::D etach Menyerahkan kepemilikan objek COM, mengembalikan penunjuk ke objek.
ptr::GetInterface Membuat instans objek COM dalam com::ptr.
ptr::QueryInterface Mengkueri objek COM yang dimiliki untuk antarmuka dan melampirkan hasilnya ke yang lain com::ptr.
ptr::Rilis Merilis semua referensi yang dimiliki pada objek COM.

Operator publik

Nama Deskripsi
ptr::operator-> Operator akses anggota, digunakan untuk memanggil metode pada objek COM yang dimiliki.
ptr::operator= Melampirkan objek COM ke com::ptr.
ptr::operator bool Operator untuk menggunakan com::ptr dalam ekspresi bersyarah.
ptr::operator! Operator untuk menentukan apakah objek COM yang dimiliki tidak valid.

Persyaratan

File header<msclr\com\ptr.h>

Namespace msclr::com

ptr::p tr

Mengembalikan penunjuk ke objek COM yang dimiliki.

ptr();
ptr(
   _interface_type * p
);

Parameter

P
Penunjuk antarmuka COM.

Keterangan

Konstruktor tanpa argumen ditetapkan ke handel objek yang mendasar nullptr . Panggilan mendatang ke com::ptr akan memvalidasi objek internal dan secara diam-diam gagal sampai objek dibuat atau dilampirkan.

Konstruktor satu argumen menambahkan referensi ke objek COM tetapi tidak merilis referensi penelepon, sehingga pemanggil harus memanggil Release objek COM untuk benar-benar menyerahkan kontrol. com::ptrKetika destruktor 's disebut akan secara otomatis merilis referensinya pada objek COM.

Meneruskan NULL ke konstruktor ini sama dengan memanggil versi tanpa argumen.

Contoh

Contoh ini mengimplementasikan kelas CLR yang menggunakan untuk membungkus com::ptr objek anggota IXMLDOMDocument privatnya. Ini menunjukkan penggunaan kedua versi konstruktor.

// comptr_ptr.cpp
// compile with: /clr /link msxml2.lib
#include <msxml2.h>
#include <msclr\com\ptr.h>

#import <msxml3.dll> raw_interfaces_only

using namespace System;
using namespace System::Runtime::InteropServices;
using namespace msclr;

// a ref class that uses a com::ptr to contain an
// IXMLDOMDocument object
ref class XmlDocument {
public:
   // construct the internal com::ptr with a null interface
   // and use CreateInstance to fill it
   XmlDocument(String^ progid) {
      m_ptrDoc.CreateInstance(progid);
   }

   // construct the internal com::ptr with a COM object
   XmlDocument(IXMLDOMDocument* pDoc) : m_ptrDoc(pDoc) {}

   // note that the destructor will call the com::ptr destructor
   // and automatically release the reference to the COM object

private:
   com::ptr<IXMLDOMDocument> m_ptrDoc;
};

// use the ref class to handle an XML DOM Document object
int main() {
   IXMLDOMDocument* pDoc = NULL;

   try {
      // create an XML DOM document object
      Marshal::ThrowExceptionForHR(CoCreateInstance(CLSID_DOMDocument30, NULL,
         CLSCTX_ALL, IID_IXMLDOMDocument, (void**)&pDoc));
      // construct the ref class with the COM object
      XmlDocument doc1(pDoc);

      // or create the class from a progid string
      XmlDocument doc2("Msxml2.DOMDocument.3.0");
   }
   // doc1 and doc2 destructors are called when they go out of scope
   // and the internal com::ptr releases its reference to the COM object
   catch (Exception^ e) {
      Console::WriteLine(e);
   }
   finally {
      if (NULL != pDoc) {
         pDoc->Release();
      }
   }
}

ptr::~ptr

com::ptrMerusak .

~ptr();

Keterangan

Pada penghancuran, com::ptr merilis semua referensi yang dimilikinya ke objek COM-nya. Dengan asumsi bahwa tidak ada referensi lain yang disimpan ke objek COM, objek COM akan dihapus dan memorinya dibebaskan.

Contoh

Contoh ini mengimplementasikan kelas CLR yang menggunakan untuk membungkus com::ptr objek anggota IXMLDOMDocument privatnya. main Dalam fungsi , destruktor dua XmlDocument objek akan dipanggil ketika mereka keluar dari cakupan try blok, yang mengakibatkan destruktor yang mendasar com::ptr dipanggil, melepaskan semua referensi yang dimiliki ke objek COM.

// comptr_dtor.cpp
// compile with: /clr /link msxml2.lib
#include <msxml2.h>
#include <msclr\com\ptr.h>

#import <msxml3.dll> raw_interfaces_only

using namespace System;
using namespace System::Runtime::InteropServices;
using namespace msclr;

// a ref class that uses a com::ptr to contain an
// IXMLDOMDocument object
ref class XmlDocument {
public:
   // construct the internal com::ptr with a null interface
   // and use CreateInstance to fill it
   XmlDocument(String^ progid) {
      m_ptrDoc.CreateInstance(progid);
   }

   // construct the internal com::ptr with a COM object
   XmlDocument(IXMLDOMDocument* pDoc) : m_ptrDoc(pDoc) {}

   // note that the destructor will call the com::ptr destructor
   // and automatically release the reference to the COM object

private:
   com::ptr<IXMLDOMDocument> m_ptrDoc;
};

// use the ref class to handle an XML DOM Document object
int main() {
   IXMLDOMDocument* pDoc = NULL;

   try {
      // create an XML DOM document object
      Marshal::ThrowExceptionForHR(CoCreateInstance(CLSID_DOMDocument30, NULL,
         CLSCTX_ALL, IID_IXMLDOMDocument, (void**)&pDoc));
      // construct the ref class with the COM object
      XmlDocument doc1(pDoc);

      // or create the class from a progid string
      XmlDocument doc2("Msxml2.DOMDocument.3.0");
   }
   // doc1 and doc2 destructors are called when they go out of scope
   // and the internal com::ptr releases its reference to the COM object
   catch (Exception^ e) {
      Console::WriteLine(e);
   }
   finally {
      if (NULL != pDoc) {
         pDoc->Release();
      }
   }
}

ptr::Lampirkan

Melampirkan objek COM ke com::ptr.

void Attach(
   _interface_type * _right
);

Parameter

_Kanan
Penunjuk antarmuka COM untuk dilampirkan.

Pengecualian

com::ptr Jika sudah memiliki referensi ke objek COM, Attach akan melempar .InvalidOperationException

Keterangan

Panggilan untuk Attach mereferensikan objek COM tetapi tidak merilis referensi pemanggil ke objek TERSEBUT.

Meneruskan NULL ke Attach tidak menghasilkan tindakan yang diambil.

Contoh

Contoh ini mengimplementasikan kelas CLR yang menggunakan untuk membungkus com::ptr objek anggota IXMLDOMDocument privatnya. Fungsi ReplaceDocument anggota pertama kali memanggil Release objek yang dimiliki sebelumnya lalu memanggil Attach untuk melampirkan objek dokumen baru.

// comptr_attach.cpp
// compile with: /clr /link msxml2.lib
#include <msxml2.h>
#include <msclr\com\ptr.h>

#import <msxml3.dll> raw_interfaces_only

using namespace System;
using namespace System::Runtime::InteropServices;
using namespace msclr;

// a ref class that uses a com::ptr to contain an
// IXMLDOMDocument object
ref class XmlDocument {
public:
   // construct the internal com::ptr with a null interface
   // and use CreateInstance to fill it
   XmlDocument(String^ progid) {
      m_ptrDoc.CreateInstance(progid);
   }

   // replace currently held COM object with another one
   void ReplaceDocument(IXMLDOMDocument* pDoc) {
      // release current document object
      m_ptrDoc.Release();
      // attach the new document object
      m_ptrDoc.Attach(pDoc);
   }

   // note that the destructor will call the com::ptr destructor
   // and automatically release the reference to the COM object

private:
   com::ptr<IXMLDOMDocument> m_ptrDoc;
};

// unmanaged function that creates a raw XML DOM Document object
IXMLDOMDocument* CreateDocument() {
   IXMLDOMDocument* pDoc = NULL;
   Marshal::ThrowExceptionForHR(CoCreateInstance(CLSID_DOMDocument30, NULL,
      CLSCTX_INPROC_SERVER, IID_IXMLDOMDocument, (void**)&pDoc));
   return pDoc;
}

// use the ref class to handle an XML DOM Document object
int main() {
   IXMLDOMDocument* pDoc = NULL;

   try {
      // create the class from a progid string
      XmlDocument doc("Msxml2.DOMDocument.3.0");

      // get another document object from unmanaged function and
      // store it in place of the one held by our ref class
      pDoc = CreateDocument();
      doc.ReplaceDocument(pDoc);
      // no further need for raw object reference
      pDoc->Release();
      pDoc = NULL;
   }
   catch (Exception^ e) {
      Console::WriteLine(e);
   }
   finally {
      if (NULL != pDoc) {
         pDoc->Release();
      }
   }
}

ptr::CreateInstance

Membuat instans objek COM dalam com::ptr.

void CreateInstance(
   System::String ^ progid,
   LPUNKNOWN pouter,
   DWORD cls_context
);
void CreateInstance(
   System::String ^ progid,
   LPUNKNOWN pouter
);
void CreateInstance(
   System::String ^ progid
);
void CreateInstance(
   const wchar_t * progid,
   LPUNKNOWN pouter,
   DWORD cls_context
);
void CreateInstance(
   const wchar_t * progid,
   LPUNKNOWN pouter
);
void CreateInstance(
   const wchar_t * progid
);
void CreateInstance(
   REFCLSID rclsid,
   LPUNKNOWN pouter,
   DWORD cls_context
);
void CreateInstance(
   REFCLSID rclsid,
   LPUNKNOWN pouter
);
void CreateInstance(
   REFCLSID rclsid
);

Parameter

progid
String ProgID.

pouter
Penunjuk ke antarmuka IUnknown objek agregat (IUnknown pengontrol). Jika pouter tidak ditentukan, NULL digunakan.

cls_context
Konteks di mana kode yang mengelola objek yang baru dibuat akan berjalan. Nilai diambil dari CLSCTX enumerasi. Jika cls_context tidak ditentukan, nilai CLSCTX_ALL digunakan.

rclsid
CLSID terkait dengan data dan kode yang akan digunakan untuk membuat objek.

Pengecualian

com::ptr Jika sudah memiliki referensi ke objek COM, CreateInstance akan melempar .InvalidOperationException

Fungsi ini memanggil CoCreateInstance dan menggunakan ThrowExceptionForHR untuk mengonversi kesalahan HRESULT apa pun ke pengecualian yang sesuai.

Keterangan

CreateInstance menggunakan untuk membuat instans CoCreateInstance baru objek yang ditentukan, yang diidentifikasi baik dari ProgID atau CLSID. Referensi com::ptr objek yang baru dibuat dan akan secara otomatis merilis semua referensi yang dimiliki setelah penghancuran.

Contoh

Contoh ini mengimplementasikan kelas CLR yang menggunakan untuk membungkus com::ptr objek anggota IXMLDOMDocument privatnya. Konstruktor kelas menggunakan dua bentuk CreateInstance berbeda untuk membuat objek dokumen baik dari ProgID atau dari CLSID ditambah CLSCTX.

// comptr_createinstance.cpp
// compile with: /clr /link msxml2.lib
#include <msxml2.h>
#include <msclr\com\ptr.h>

#import <msxml3.dll> raw_interfaces_only

using namespace System;
using namespace System::Runtime::InteropServices;
using namespace msclr;

// a ref class that uses a com::ptr to contain an
// IXMLDOMDocument object
ref class XmlDocument {
public:
   // construct the internal com::ptr with a null interface
   // and use CreateInstance to fill it
   XmlDocument(String^ progid) {
      m_ptrDoc.CreateInstance(progid);
   }
   XmlDocument(REFCLSID clsid, DWORD clsctx) {
      m_ptrDoc.CreateInstance(clsid, NULL, clsctx);
   }

   // note that the destructor will call the com::ptr destructor
   // and automatically release the reference to the COM object

private:
   com::ptr<IXMLDOMDocument> m_ptrDoc;
};

// use the ref class to handle an XML DOM Document object
int main() {
   try {
      // create the class from a progid string
      XmlDocument doc1("Msxml2.DOMDocument.3.0");

      // or from a clsid with specific CLSCTX
      XmlDocument doc2(CLSID_DOMDocument30, CLSCTX_INPROC_SERVER);
   }
   catch (Exception^ e) {
      Console::WriteLine(e);
   }
}

ptr::D etach

Menyerahkan kepemilikan objek COM, mengembalikan penunjuk ke objek.

_interface_type * Detach();

Nilai hasil

Penunjuk ke objek COM.

Jika tidak ada objek yang dimiliki, NULL dikembalikan.

Pengecualian

Secara internal, QueryInterface dipanggil pada objek COM yang dimiliki dan kesalahan HRESULT apa pun dikonversi ke pengecualian oleh ThrowExceptionForHR.

Keterangan

Detach pertama menambahkan referensi ke objek COM atas nama pemanggil dan kemudian merilis semua referensi yang dimiliki oleh com::ptr. Penelepon pada akhirnya harus melepaskan objek yang dikembalikan untuk menghancurkannya.

Contoh

Contoh ini mengimplementasikan kelas CLR yang menggunakan untuk membungkus com::ptr objek anggota IXMLDOMDocument privatnya. Fungsi DetachDocument anggota memanggil Detach untuk menyerahkan kepemilikan objek COM dan mengembalikan penunjuk ke pemanggil.

// comptr_detach.cpp
// compile with: /clr /link msxml2.lib
#include <msxml2.h>
#include <msclr\com\ptr.h>

#import <msxml3.dll> raw_interfaces_only

using namespace System;
using namespace System::Runtime::InteropServices;
using namespace msclr;

// a ref class that uses a com::ptr to contain an
// IXMLDOMDocument object
ref class XmlDocument {
public:
   // construct the internal com::ptr with a null interface
   // and use CreateInstance to fill it
   XmlDocument(String^ progid) {
      m_ptrDoc.CreateInstance(progid);
   }

   // detach the COM object and return it
   // this releases the internal reference to the object
   IXMLDOMDocument* DetachDocument() {
      return m_ptrDoc.Detach();
   }

   // note that the destructor will call the com::ptr destructor
   // and automatically release the reference to the COM object

private:
   com::ptr<IXMLDOMDocument> m_ptrDoc;
};

// unmanaged function that loads XML into a raw XML DOM Document object
HRESULT LoadXml(IXMLDOMDocument* pDoc, BSTR bstrXml) {
   HRESULT hr = S_OK;
   VARIANT_BOOL bSuccess;
   hr = pDoc->loadXML(bstrXml, &bSuccess);
   if (S_OK == hr && !bSuccess) {
      hr = E_FAIL;
   }
   return hr;
}

// use the ref class to handle an XML DOM Document object
int main() {
   IXMLDOMDocument* pDoc = NULL;
   BSTR bstrXml = NULL;

   try {
      // create the class from a progid string
      XmlDocument doc("Msxml2.DOMDocument.3.0");

      bstrXml = ::SysAllocString(L"<word>persnickety</word>");
      if (NULL == bstrXml) {
         throw gcnew OutOfMemoryException("bstrXml");
      }
      // detach the document object from the ref class
      pDoc = doc.DetachDocument();
      // use unmanaged function and raw object to load xml
      Marshal::ThrowExceptionForHR(LoadXml(pDoc, bstrXml));
      // release document object as the ref class no longer owns it
      pDoc->Release();
      pDoc = NULL;
   }
   catch (Exception^ e) {
      Console::WriteLine(e);
   }
   finally {
      if (NULL != pDoc) {
         pDoc->Release();
      }

   }
}

ptr::GetInterface

Mengembalikan penunjuk ke objek COM yang dimiliki.

_interface_type * GetInterface();

Nilai hasil

Penunjuk ke objek COM yang dimiliki.

Pengecualian

Secara internal, QueryInterface dipanggil pada objek COM yang dimiliki dan kesalahan HRESULT apa pun dikonversi ke pengecualian oleh ThrowExceptionForHR.

Keterangan

menambahkan com::ptr referensi ke objek COM atas nama pemanggil dan juga menyimpan referensinya sendiri pada objek COM. Penelepon pada akhirnya harus merilis referensi pada objek yang dikembalikan atau tidak akan pernah dihancurkan.

Contoh

Contoh ini mengimplementasikan kelas CLR yang menggunakan untuk membungkus com::ptr objek anggota IXMLDOMDocument privatnya. Fungsi GetDocument anggota menggunakan GetInterface untuk mengembalikan penunjuk ke objek COM.

// comptr_getinterface.cpp
// compile with: /clr /link msxml2.lib
#include <msxml2.h>
#include <msclr\com\ptr.h>

#import <msxml3.dll> raw_interfaces_only

using namespace System;
using namespace System::Runtime::InteropServices;
using namespace msclr;

// a ref class that uses a com::ptr to contain an
// IXMLDOMDocument object
ref class XmlDocument {
public:
   // construct the internal com::ptr with a null interface
   // and use CreateInstance to fill it
   XmlDocument(String^ progid) {
      m_ptrDoc.CreateInstance(progid);
   }

   // add a reference to and return the COM object
   // but keep an internal reference to the object
   IXMLDOMDocument* GetDocument() {
      return m_ptrDoc.GetInterface();
   }

   // simplified function that only writes the first node
   void WriteDocument() {
      IXMLDOMNode* pNode = NULL;
      BSTR bstr = NULL;

      try {
         // use operator -> to call XML Doc member
         Marshal::ThrowExceptionForHR(m_ptrDoc->get_firstChild(&pNode));
         if (NULL != pNode) {
            // write out the xml
            Marshal::ThrowExceptionForHR(pNode->get_nodeName(&bstr));
            String^ strName = gcnew String(bstr);
            Console::Write("<{0}>", strName);
            ::SysFreeString(bstr);
            bstr = NULL;

            Marshal::ThrowExceptionForHR(pNode->get_text(&bstr));
            Console::Write(gcnew String(bstr));
            ::SysFreeString(bstr);
            bstr = NULL;

            Console::WriteLine("</{0}>", strName);
         }
      }
      finally {
         if (NULL != pNode) {
            pNode->Release();
         }
         ::SysFreeString(bstr);
      }
   }

   // note that the destructor will call the com::ptr destructor
   // and automatically release the reference to the COM object

private:
   com::ptr<IXMLDOMDocument> m_ptrDoc;
};

// unmanaged function that loads XML into a raw XML DOM Document object
HRESULT LoadXml(IXMLDOMDocument* pDoc, BSTR bstrXml) {
   HRESULT hr = S_OK;
   VARIANT_BOOL bSuccess;
   hr = pDoc->loadXML(bstrXml, &bSuccess);
   if (S_OK == hr && !bSuccess) {
      hr = E_FAIL;
   }
   return hr;
}

// use the ref class to handle an XML DOM Document object
int main() {
   IXMLDOMDocument* pDoc = NULL;
   BSTR bstrXml = NULL;

   try {
      // create the class from a progid string
      XmlDocument doc("Msxml2.DOMDocument.3.0");

      bstrXml = ::SysAllocString(L"<word>persnickety</word>");
      if (NULL == bstrXml) {
         throw gcnew OutOfMemoryException("bstrXml");
      }
      // detach the document object from the ref class
      pDoc = doc.GetDocument();
      // use unmanaged function and raw object to load xml
      Marshal::ThrowExceptionForHR(LoadXml(pDoc, bstrXml));
      // release reference to document object (but ref class still references it)
      pDoc->Release();
      pDoc = NULL;

      // call another function on the ref class
      doc.WriteDocument();
   }
   catch (Exception^ e) {
      Console::WriteLine(e);
   }
   finally {
      if (NULL != pDoc) {
         pDoc->Release();
      }

   }
}
<word>persnickety</word>

ptr::QueryInterface

Mengkueri objek COM yang dimiliki untuk antarmuka dan melampirkan hasilnya ke yang lain com::ptr.

template<class _other_type>
void QueryInterface(
   ptr<_other_type> % other
);

Parameter

lain
Yang com::ptr akan mendapatkan antarmuka.

Pengecualian

Secara internal, QueryInterface dipanggil pada objek COM yang dimiliki dan kesalahan HRESULT apa pun dikonversi ke pengecualian oleh ThrowExceptionForHR.

Keterangan

Gunakan metode ini untuk membuat pembungkus COM untuk antarmuka objek COM yang berbeda yang dimiliki oleh pembungkus saat ini. Metode ini memanggil QueryInterface melalui objek COM yang dimiliki untuk meminta penunjuk ke antarmuka tertentu dari objek COM dan melampirkan penunjuk antarmuka yang dikembalikan ke yang diteruskan com::ptr.

Contoh

Contoh ini mengimplementasikan kelas CLR yang menggunakan untuk membungkus com::ptr objek anggota IXMLDOMDocument privatnya. Fungsi WriteTopLevelNode anggota menggunakan QueryInterface untuk mengisi lokal com::ptr dengan IXMLDOMNode lalu meneruskan com::ptr (dengan melacak referensi) ke fungsi anggota privat yang menulis nama node dan properti teks ke konsol.

// comptr_queryinterface.cpp
// compile with: /clr /link msxml2.lib
#include <msxml2.h>
#include <msclr\com\ptr.h>

#import <msxml3.dll> raw_interfaces_only

using namespace System;
using namespace System::Runtime::InteropServices;
using namespace msclr;

// a ref class that uses a com::ptr to contain an
// IXMLDOMDocument object
ref class XmlDocument {
public:
   // construct the internal com::ptr with a null interface
   // and use CreateInstance to fill it
   XmlDocument(String^ progid) {
      m_ptrDoc.CreateInstance(progid);
   }

   void LoadXml(String^ xml) {
      pin_ptr<const wchar_t> pinnedXml = PtrToStringChars(xml);
      BSTR bstr = NULL;

      try {
         // load some XML into our document
         bstr = ::SysAllocString(pinnedXml);
         if (NULL == bstr) {
            throw gcnew OutOfMemoryException;
         }
         VARIANT_BOOL bIsSuccessful = false;
         // use operator -> to call IXMODOMDocument member function
         Marshal::ThrowExceptionForHR(m_ptrDoc->loadXML(bstr, &bIsSuccessful));
      }
      finally {
         ::SysFreeString(bstr);
      }
   }

   // write the top level node to the console
   void WriteTopLevelNode() {
      com::ptr<IXMLDOMNode> ptrNode;

      // query for the top level node interface
      m_ptrDoc.QueryInterface(ptrNode);
      WriteNode(ptrNode);
   }

   // note that the destructor will call the com::ptr destructor
   // and automatically release the reference to the COM object

private:
   // simplified function that only writes the node
   void WriteNode(com::ptr<IXMLDOMNode> % node) {
      BSTR bstr = NULL;

      try {
         // write out the name and text properties
         Marshal::ThrowExceptionForHR(node->get_nodeName(&bstr));
         String^ strName = gcnew String(bstr);
         Console::Write("<{0}>", strName);
         ::SysFreeString(bstr);
         bstr = NULL;

         Marshal::ThrowExceptionForHR(node->get_text(&bstr));
         Console::Write(gcnew String(bstr));
         ::SysFreeString(bstr);
         bstr = NULL;

         Console::WriteLine("</{0}>", strName);
      }
      finally {
         ::SysFreeString(bstr);
      }
   }

   com::ptr<IXMLDOMDocument> m_ptrDoc;
};

// use the ref class to handle an XML DOM Document object
int main() {
   try {
      // create the class from a progid string
      XmlDocument doc("Msxml2.DOMDocument.3.0");

      // stream some xml into the document
      doc.LoadXml("<word>persnickety</word>");

      // write the document to the console
      doc.WriteTopLevelNode();
   }
   catch (Exception^ e) {
      Console::WriteLine(e);
   }
}
<#document>persnickety</#document>

ptr::Rilis

Merilis semua referensi yang dimiliki pada objek COM.

void Release();

Keterangan

Memanggil fungsi ini merilis semua referensi yang dimiliki pada objek COM dan mengatur handel internal ke objek COM ke nullptr. Jika tidak ada referensi lain pada objek COM, itu akan dihancurkan.

Contoh

Contoh ini mengimplementasikan kelas CLR yang menggunakan untuk membungkus com::ptr objek anggota IXMLDOMDocument privatnya. Fungsi ReplaceDocument anggota menggunakan untuk merilis Release objek dokumen sebelumnya sebelum melampirkan dokumen baru.

// comptr_release.cpp
// compile with: /clr /link msxml2.lib
#include <msxml2.h>
#include <msclr\com\ptr.h>

#import <msxml3.dll> raw_interfaces_only

using namespace System;
using namespace System::Runtime::InteropServices;
using namespace msclr;

// a ref class that uses a com::ptr to contain an
// IXMLDOMDocument object
ref class XmlDocument {
public:
   // construct the internal com::ptr with a null interface
   // and use CreateInstance to fill it
   XmlDocument(String^ progid) {
      m_ptrDoc.CreateInstance(progid);
   }

   // replace currently held COM object with another one
   void ReplaceDocument(IXMLDOMDocument* pDoc) {
      // release current document object
      m_ptrDoc.Release();
      // attach the new document object
      m_ptrDoc.Attach(pDoc);
   }

   // note that the destructor will call the com::ptr destructor
   // and automatically release the reference to the COM object

private:
   com::ptr<IXMLDOMDocument> m_ptrDoc;
};

// unmanaged function that creates a raw XML DOM Document object
IXMLDOMDocument* CreateDocument() {
   IXMLDOMDocument* pDoc = NULL;
   Marshal::ThrowExceptionForHR(CoCreateInstance(CLSID_DOMDocument30, NULL,
      CLSCTX_INPROC_SERVER, IID_IXMLDOMDocument, (void**)&pDoc));
   return pDoc;
}

// use the ref class to handle an XML DOM Document object
int main() {
   IXMLDOMDocument* pDoc = NULL;

   try {
      // create the class from a progid string
      XmlDocument doc("Msxml2.DOMDocument.3.0");

      // get another document object from unmanaged function and
      // store it in place of the one held by our ref class
      pDoc = CreateDocument();
      doc.ReplaceDocument(pDoc);
      // no further need for raw object reference
      pDoc->Release();
      pDoc = NULL;
   }
   catch (Exception^ e) {
      Console::WriteLine(e);
   }
   finally {
      if (NULL != pDoc) {
         pDoc->Release();
      }
   }
}

ptr::operator->

Operator akses anggota, digunakan untuk memanggil metode pada objek COM yang dimiliki.

_detail::smart_com_ptr<_interface_type> operator->();

Nilai hasil

A smart_com_ptr ke objek COM.

Pengecualian

Secara internal, QueryInterface dipanggil pada objek COM yang dimiliki dan kesalahan HRESULT apa pun dikonversi ke pengecualian oleh ThrowExceptionForHR.

Keterangan

Operator ini memungkinkan Anda untuk memanggil metode objek COM yang dimiliki. Ini mengembalikan sementara smart_com_ptr yang secara otomatis menangani sendiri AddRef dan Release.

Contoh

Contoh ini mengimplementasikan kelas CLR yang menggunakan untuk membungkus com::ptr objek anggota IXMLDOMDocument privatnya. Fungsi ini WriteDocument menggunakan operator-> untuk memanggil get_firstChild anggota objek dokumen.

// comptr_op_member.cpp
// compile with: /clr /link msxml2.lib
#include <msxml2.h>
#include <msclr\com\ptr.h>

#import <msxml3.dll> raw_interfaces_only

using namespace System;
using namespace System::Runtime::InteropServices;
using namespace msclr;

// a ref class that uses a com::ptr to contain an
// IXMLDOMDocument object
ref class XmlDocument {
public:
   // construct the internal com::ptr with a null interface
   // and use CreateInstance to fill it
   XmlDocument(String^ progid) {
      m_ptrDoc.CreateInstance(progid);
   }

   // add a reference to and return the COM object
   // but keep an internal reference to the object
   IXMLDOMDocument* GetDocument() {
      return m_ptrDoc.GetInterface();
   }

   // simplified function that only writes the first node
   void WriteDocument() {
      IXMLDOMNode* pNode = NULL;
      BSTR bstr = NULL;

      try {
         // use operator -> to call XML Doc member
         Marshal::ThrowExceptionForHR(m_ptrDoc->get_firstChild(&pNode));
         if (NULL != pNode) {
            // write out the xml
            Marshal::ThrowExceptionForHR(pNode->get_nodeName(&bstr));
            String^ strName = gcnew String(bstr);
            Console::Write("<{0}>", strName);
            ::SysFreeString(bstr);
            bstr = NULL;

            Marshal::ThrowExceptionForHR(pNode->get_text(&bstr));
            Console::Write(gcnew String(bstr));
            ::SysFreeString(bstr);
            bstr = NULL;

            Console::WriteLine("</{0}>", strName);
         }
      }
      finally {
         if (NULL != pNode) {
            pNode->Release();
         }
         ::SysFreeString(bstr);
      }
   }

   // note that the destructor will call the com::ptr destructor
   // and automatically release the reference to the COM object

private:
   com::ptr<IXMLDOMDocument> m_ptrDoc;
};

// unmanaged function that loads XML into a raw XML DOM Document object
HRESULT LoadXml(IXMLDOMDocument* pDoc, BSTR bstrXml) {
   HRESULT hr = S_OK;
   VARIANT_BOOL bSuccess;
   hr = pDoc->loadXML(bstrXml, &bSuccess);
   if (S_OK == hr && !bSuccess) {
      hr = E_FAIL;
   }
   return hr;
}

// use the ref class to handle an XML DOM Document object
int main() {
   IXMLDOMDocument* pDoc = NULL;
   BSTR bstrXml = NULL;

   try {
      // create the class from a progid string
      XmlDocument doc("Msxml2.DOMDocument.3.0");

      bstrXml = ::SysAllocString(L"<word>persnickety</word>");
      if (NULL == bstrXml) {
         throw gcnew OutOfMemoryException("bstrXml");
      }
      // detach the document object from the ref class
      pDoc = doc.GetDocument();
      // use unmanaged function and raw object to load xml
      Marshal::ThrowExceptionForHR(LoadXml(pDoc, bstrXml));
      // release reference to document object (but ref class still references it)
      pDoc->Release();
      pDoc = NULL;

      // call another function on the ref class
      doc.WriteDocument();
   }
   catch (Exception^ e) {
      Console::WriteLine(e);
   }
   finally {
      if (NULL != pDoc) {
         pDoc->Release();
      }

   }
}
<word>persnickety</word>

ptr::operator=

Melampirkan objek COM ke com::ptr.

ptr<_interface_type> % operator=(
   _interface_type * _right
);

Parameter

_Kanan
Penunjuk antarmuka COM untuk dilampirkan.

Nilai hasil

Referensi pelacakan pada com::ptr.

Pengecualian

com::ptr Jika sudah memiliki referensi ke objek COM, operator= akan melempar .InvalidOperationException

Keterangan

Menetapkan objek COM ke com::ptr referensi objek COM tetapi tidak merilis referensi pemanggil ke objek TERSEBUT.

Operator ini memiliki efek yang sama dengan Attach.

Contoh

Contoh ini mengimplementasikan kelas CLR yang menggunakan untuk membungkus com::ptr objek anggota IXMLDOMDocument privatnya. Fungsi ReplaceDocument anggota pertama kali memanggil Release objek yang dimiliki sebelumnya lalu menggunakan operator= untuk melampirkan objek dokumen baru.

// comptr_op_assign.cpp
// compile with: /clr /link msxml2.lib
#include <msxml2.h>
#include <msclr\com\ptr.h>

#import <msxml3.dll> raw_interfaces_only

using namespace System;
using namespace System::Runtime::InteropServices;
using namespace msclr;

// a ref class that uses a com::ptr to contain an
// IXMLDOMDocument object
ref class XmlDocument {
public:
   // construct the internal com::ptr with a null interface
   // and use CreateInstance to fill it
   XmlDocument(String^ progid) {
      m_ptrDoc.CreateInstance(progid);
   }

   // replace currently held COM object with another one
   void ReplaceDocument(IXMLDOMDocument* pDoc) {
      // release current document object
      m_ptrDoc.Release();
      // attach the new document object
      m_ptrDoc = pDoc;
   }

   // note that the destructor will call the com::ptr destructor
   // and automatically release the reference to the COM object

private:
   com::ptr<IXMLDOMDocument> m_ptrDoc;
};

// unmanaged function that creates a raw XML DOM Document object
IXMLDOMDocument* CreateDocument() {
   IXMLDOMDocument* pDoc = NULL;
   Marshal::ThrowExceptionForHR(CoCreateInstance(CLSID_DOMDocument30, NULL,
      CLSCTX_INPROC_SERVER, IID_IXMLDOMDocument, (void**)&pDoc));
   return pDoc;
}

// use the ref class to handle an XML DOM Document object
int main() {
   IXMLDOMDocument* pDoc = NULL;

   try {
      // create the class from a progid string
      XmlDocument doc("Msxml2.DOMDocument.3.0");

      // get another document object from unmanaged function and
      // store it in place of the one held by the ref class
      pDoc = CreateDocument();
      doc.ReplaceDocument(pDoc);
      // no further need for raw object reference
      pDoc->Release();
      pDoc = NULL;
   }
   catch (Exception^ e) {
      Console::WriteLine(e);
   }
   finally {
      if (NULL != pDoc) {
         pDoc->Release();
      }
   }
}

ptr::operator bool

Operator untuk menggunakan com::ptr dalam ekspresi bersyarah.

operator bool();

Nilai hasil

true jika objek COM yang dimiliki valid; false Sebaliknya.

Keterangan

Objek COM yang dimiliki valid jika bukan nullptr.

Operator ini mengonversi yang _detail_class::_safe_bool lebih aman daripada bool karena tidak dapat dikonversi ke jenis integral.

Contoh

Contoh ini mengimplementasikan kelas CLR yang menggunakan untuk membungkus com::ptr objek anggota IXMLDOMDocument privatnya. Fungsi CreateInstance anggota menggunakan operator bool setelah membuat objek dokumen baru untuk menentukan apakah itu valid dan menulis ke konsol jika ya.

// comptr_op_bool.cpp
// compile with: /clr /link msxml2.lib
#include <msxml2.h>
#include <msclr\com\ptr.h>

#import <msxml3.dll> raw_interfaces_only

using namespace System;
using namespace System::Runtime::InteropServices;
using namespace msclr;

// a ref class that uses a com::ptr to contain an
// IXMLDOMDocument object
ref class XmlDocument {
public:
   void CreateInstance(String^ progid) {
      if (!m_ptrDoc) {
         m_ptrDoc.CreateInstance(progid);
         if (m_ptrDoc) { // uses operator bool
            Console::WriteLine("DOM Document created.");
         }
      }
   }

   // note that the destructor will call the com::ptr destructor
   // and automatically release the reference to the COM object

private:
   com::ptr<IXMLDOMDocument> m_ptrDoc;
};

// use the ref class to handle an XML DOM Document object
int main() {
   try {
      XmlDocument doc;
      // create the instance from a progid string
      doc.CreateInstance("Msxml2.DOMDocument.3.0");
   }
   catch (Exception^ e) {
      Console::WriteLine(e);
   }
}
DOM Document created.

ptr::operator!

Operator untuk menentukan apakah objek COM yang dimiliki tidak valid.

bool operator!();

Nilai hasil

true jika objek COM yang dimiliki tidak valid; false Sebaliknya.

Keterangan

Objek COM yang dimiliki valid jika bukan nullptr.

Contoh

Contoh ini mengimplementasikan kelas CLR yang menggunakan untuk membungkus com::ptr objek anggota IXMLDOMDocument privatnya. Fungsi CreateInstance anggota menggunakan operator! untuk menentukan apakah objek dokumen sudah dimiliki, dan hanya membuat instans baru jika objek tidak valid.

// comptr_op_not.cpp
// compile with: /clr /link msxml2.lib
#include <msxml2.h>
#include <msclr\com\ptr.h>

#import <msxml3.dll> raw_interfaces_only

using namespace System;
using namespace System::Runtime::InteropServices;
using namespace msclr;

// a ref class that uses a com::ptr to contain an
// IXMLDOMDocument object
ref class XmlDocument {
public:
   void CreateInstance(String^ progid) {
      if (!m_ptrDoc) {
         m_ptrDoc.CreateInstance(progid);
         if (m_ptrDoc) {
            Console::WriteLine("DOM Document created.");
         }
      }
   }

   // note that the destructor will call the com::ptr destructor
   // and automatically release the reference to the COM object

private:
   com::ptr<IXMLDOMDocument> m_ptrDoc;
};

// use the ref class to handle an XML DOM Document object
int main() {
   try {
      XmlDocument doc;
      // create the instance from a progid string
      doc.CreateInstance("Msxml2.DOMDocument.3.0");
   }
   catch (Exception^ e) {
      Console::WriteLine(e);
   }
}
DOM Document created.