Megjegyzés
Az oldalhoz való hozzáféréshez engedély szükséges. Megpróbálhat bejelentkezni vagy módosítani a címtárat.
Az oldalhoz való hozzáféréshez engedély szükséges. Megpróbálhatja módosítani a címtárat.
A C++/WinRT későbbi verzióinak megjelenésekor ez a témakör ismerteti az újdonságokat és a megváltozott változásokat.
A legutóbbi fejlesztések/kiegészítések összesítése 2020 márciusától
Akár 23% rövidebb buildelési idő
A C++/WinRT és a C++ fordítócsapatok együttműködve mindent megtesznek a létrehozási idő lerövidítése érdekében. A fordítóelemzésen áthatoltuk, hogy a C++/WinRT belső elemei hogyan strukturálhatók át, hogy a C++ fordító kiküszöbölje a fordítási idő terhelését, valamint hogy maga a C++ fordító hogyan fejleszthető a C++/WinRT-kódtár kezeléséhez. A C++/WinRT a fordítóhoz lett optimalizálva; és a fordító a C++/WinRT-hez lett optimalizálva.
Vegyük például egy előre lefordított fejléc (PCH) létrehozásának legrosszabb esetét, amely minden egyes C++/WinRT-vetítési névtérfejlécet tartalmaz.
| verzió | PCH-méret (bájt) | Idő (ek) |
|---|---|---|
| C++/WinRT júliustól a Visual C++ 16.3-val | 3,004,104,632 | 31 |
| A C++/WinRT 2.0.200316.3-os verziója a Visual C++ 16.5-ös verziójával | 2,393,515,336 | 24 |
20% méretcsökkenés, és 23% a buildelési idő csökkentése.
Továbbfejlesztett MSBuild-támogatás
Sok munkát fektettünk az MSBuild támogatásának fejlesztésébe számos különböző forgatókönyv esetében.
Még gyorsabb gyári gyorsítótárazás
Továbbfejlesztettük a gyári gyorsítótárat a jobb beágyazott gyorselérési utak érdekében, ami gyorsabb végrehajtáshoz vezet.
Ez a fejlesztés nincs hatással a kódméretre — ahogy azt az alábbi Optimalizált EH-kódgenerálás szakaszban ismertetjük, ha az alkalmazása nagymértékben használ C++ kivételkezelést, akkor a bináris méretét csökkentheti a /d2FH4 kapcsoló használatával, amely alapértelmezés szerint be van kapcsolva a Visual Studio 2019 16.3-as és újabb verzióival létrehozott új projektekben.
Hatékonyabb boxolás
XAML-alkalmazásokban való használat esetén a winrt::box_value mostantól hatékonyabb (lásd: Boxing and unboxing). Azok az alkalmazások, amelyek sok ökölvívást végeznek, a kódméret csökkenését is észlelik.
Az IInspectable felületet megvalósító COM-interfészek implementálásának támogatása
Ha egy (nemWindows-Runtime) COM-felületet kell implementálnia, amely éppen az IInspectable implementálásához szükséges, akkor ezt most a C++/WinRT használatával teheti meg. Lásd az IInspectable-t implementáló COM-felületeket.
Modulzárolási fejlesztések
A modulzárolás szabályozása mostantól lehetővé teszi az egyéni üzemeltetési forgatókönyveket és a modulszintű zárolás teljes megszüntetését is. Lásd a modulzárolási fejlesztéseket.
A nem Windows Runtime-eredetű hibainformációk támogatása
Egyes API-k (még Windows-futtatókörnyezet API-k is) Windows-futtatókörnyezet hibakeresési API-k használata nélkül jelentik a hibákat. Ilyen esetekben a C++/WinRT mostantól visszaesik a COM-hibainformációk használatára. Lásd: A nem WinRT típusú hibainformációk C++/WinRT-támogatása.
C++ modul támogatásának engedélyezése
A C++ modul támogatása visszatért, de csak kísérleti formában. A funkció még nem fejeződött be a C++ fordítóban.
Hatékonyabb coroutine újraindulása
A C++/WinRT coroutines már jól teljesít, de továbbra is keressük a megoldási lehetőségeket. Lásd: A koroutin újraindulásának méretezhetőségének javítása.
Új when_all és when_any aszinkron segítők
A(z) when_all segédfüggvény egy IAsyncAction objektumot hoz létre, amely akkor fejeződik be, amikor az összes megadott awaitelhető objektum befejeződik. A when_any segédfüggvény egy IAsyncAction műveletet hoz létre, amely akkor fejeződik be, amikor a megadott várható objektumok bármelyike befejeződött.
Lásd: A when_any aszinkron segédfüggvény hozzáadása és A when_all aszinkron segédfüggvény hozzáadása.
Egyéb optimalizálások és kiegészítések
Emellett számos hibajavítást és kisebb optimalizálást és kiegészítést vezettek be, beleértve a hibakeresés egyszerűsítését és a belső és alapértelmezett implementációk optimalizálását célzó különböző fejlesztéseket. A teljes listát a következő hivatkozáson találja: https://github.com/microsoft/xlang/pulls?q=is%3Apr+is%3Aclosed.
Hírek és változások a C++/WinRT 2.0-ban
A C++/WinRT Visual Studio-bővítményről (VSIX), a Microsoft.Windows.CppWinRT NuGet-csomagról és a(z) cppwinrt.exe eszközről — beleértve azok beszerzésének és telepítésének módját is — további információkért lásd: A Visual Studio C++/WinRT, XAML, a VSIX-bővítmény és a NuGet-csomag támogatása.
A 2.0-s verzió C++/WinRT Visual Studio bővítményének (VSIX) módosítása
- A hibakereső vizualizáló mostantól a Visual Studio 2019-et is támogatja, miközben továbbra is támogatja a Visual Studio 2017-et.
- Számos hibajavítás történt.
A Microsoft.Windows.CppWinRT NuGet-csomag 2.0-s verziójának változásai
- A
cppwinrt.exeeszköz mostantól a Microsoft.Windows.CppWinRT NuGet-csomag része, és igény szerint platformprojekciós fejléceket hoz létre minden projekthez. Következésképpen azcppwinrt.exeeszköz már nem függ a Windows SDK-tól (bár a szerszám kompatibilitási okokból továbbra is az SDK-val szállít). -
cppwinrt.exeMostantól az egyes platformok/konfigurációspecifikus köztes mappák ($IntDir) alá vetítésfejléceket hoz létre a párhuzamos buildek engedélyezéséhez. - A C++/WinRT buildtámogatás (props/targets) már teljes mértékben dokumentálva van, ha manuálisan szeretné testre szabni a projektfájlokat. Lásd a Microsoft.Windows.CppWinRT NuGet-csomag readme fájlját.
- Számos hibajavítás történt.
A C++/WinRT módosítása a 2.0-s verzióhoz
Nyílt forráskód
Az cppwinrt.exe eszköz egy Windows-futtatókörnyezet metaadatfájlt (.winmd) használ, és egy fejlécfájl-alapú standard C++ kódtárat hoz létre belőle, amely a metaadatokban leírt API-kat projekteli. Így ezeket az API-kat a C++/WinRT-kódból is felhasználhatja.
Ez az eszköz most már egy teljes egészében nyílt forráskód projekt, amely GitHub érhető el. Látogasson el a Microsoft/cppwinrt oldalra.
xlang-kódtárak
A Windows-futtatókörnyezet által használt ECMA-335 metaadatformátum elemzésére szolgáló, teljesen hordozható, kizárólag fejlécfájlokból álló kódtár képezi majd az összes Windows-futtatókörnyezet- és xlang-eszköz alapját a jövőben. Figyelemre méltó, hogy a cppwinrt.exe eszközt is teljesen újraírtuk az xlang könyvtárak felhasználásával. Ez sokkal pontosabb metaadat-lekérdezéseket biztosít, és a C++/WinRT nyelvi előrejelzéssel kapcsolatos néhány régóta fennálló problémát old meg.
Kevesebb függőség
Az xlang metaadat-olvasója miatt maga az cppwinrt.exe eszköz kevesebb függőséget vesz fel. Ez sokkal rugalmasabbá teszi, és több forgatókönyvben is használható – különösen korlátozott buildkörnyezetekben. Fontos, hogy többé már nem támaszkodik a(z) RoMetadata.dll elemre.
Ezek a cppwinrt.exe 2.0 függőségei.
- ADVAPI32.dll
- KERNEL32.dll
- SHLWAPI.dll
- XmlLite.dll
Ezek a DLL-ek nem csak Windows 10 érhetők el, hanem egészen a Windows 7 ig, sőt Windows Vista is. Ha szeretné, a régi, Windows 7 futó buildkiszolgáló mostantól képes Ccppwinrt.exe++ fejléceket létrehozni a projekthez. Egy kis munkával a C++/WinRT-t is futtathatja Windows 7, ha ez érdekli.
Hasonlítsa össze a fenti listát ezekkel a függőségekkel, amelyekkel cppwinrt.exe az 1.0 rendelkezik.
- ADVAPI32.dll
- SHELL32.dll
- api-ms-win-core-file-l1-1-0.dll
- XmlLite.dll
- api-ms-win-core-libraryloader-l1-2-0.dll
- api-ms-win-core-processenvironment-l1-1-0.dll
- RoMetadata.dll
- SHLWAPI.dll
- KERNEL32.dll
- api-ms-win-core-rtlsupport-l1-1-0.dll
- api-ms-win-core-heap-l1-1-0.dll
- api-ms-win-core-timezone-l1-1-0.dll
- api-ms-win-core-console-l1-1-0.dll
- api-ms-win-core-localization-l1-2-0.dll
- OLEAUT32.dll
- api-ms-win-core-winrt-error-l1-1-0.dll
- api-ms-win-core-winrt-error-l1-1-1.dll
- api-ms-win-core-winrt-l1-1-0.dll
- api-ms-win-core-winrt-string-l1-1-0.dll
- api-ms-win-core-synch-l1-1-0.dll
- api-ms-win-core-threadpool-l1-2-0.dll
- api-ms-win-core-com-l1-1-0.dll
- api-ms-win-core-com-l1-1-1.dll
- api-ms-win-core-synch-l1-2-0.dll
A Windows-futtatókörnyezet noexcept attribútum
A Windows-futtatókörnyezet egy új [noexcept] attribútummal rendelkezik, amellyel a metódusokat és tulajdonságokat a MIDL 3.0-ban díszítheti. Az attribútum jelenléte azt jelzi a támogató eszközöknek, hogy az implementáció nem ad kivételt (és nem ad vissza sikertelen HRESULT-t). Ez lehetővé teszi, hogy a nyelvi előrejelzések optimalizálják a kódlétrehozást azáltal, hogy elkerülik az alkalmazás bináris felületének (ABI)-hívások támogatásához szükséges kivételkezelési többletterhelést, amely esetleg meghiúsulhat.
A C++/WinRT kihasználja ezt azáltal, hogy C++ noexcept implementációkat hoz létre mind a fogyasztó, mind a szerzői kódhoz. Ha vannak olyan hibamentes API-metódusai vagy -tulajdonságai, és a kódméret is fontos szempont, akkor érdemes megvizsgálnia ezt az attribútumot.
Optimalizált kódgenerálás
A C++/WinRT mostantól még hatékonyabb C++ forráskódot hoz létre (a színfalak mögött), hogy a C++ fordító a lehető legkisebb és leghatékonyabb bináris kódot hozza létre. Számos fejlesztés célja a kivételkezelés költségeinek csökkentése a szükségtelen visszatekerés elkerülése érdekében. A nagy mennyiségű C++/WinRT-kódot használó bináris fájlok nagyjából 4% csökkentik a kód méretét. A kód a csökkentett utasításszám miatt hatékonyabb is (gyorsabban fut).
Ezek a fejlesztések az Ön számára is elérhető új interop funkcióra támaszkodnak. Az erőforrás-tulajdonosok összes C++/WinRT-típusa tartalmaz egy konstruktort, amely közvetlenül veszi át a tulajdonjogot, elkerülve az előző kétlépéses megközelítést.
ABI::Windows::Foundation::IStringable* raw = ...
IStringable projected(raw, take_ownership_from_abi);
printf("%ls\n", projected.ToString().c_str());
Optimalizált kivételkezelési (EH) kódgenerálás
Ez a módosítás kiegészíti a Microsoft C++ optimalizáló csapat által a kivételkezelés költségeinek csökkentése érdekében végzett munkát. Ha nagy mértékben használ alkalmazásbináris felületeket (ABI-ket) — például a COM-ot — a kódjában, akkor sok, ezt a mintát követő kóddal fog találkozni.
int32_t Function() noexcept
{
try
{
// code here constitutes unique value.
}
catch (...)
{
// code here is always duplicated.
}
}
A C++/WinRT maga hozza létre ezt a mintát minden implementált API-hoz. Több ezer API-függvény esetén az itt található optimalizálás jelentős lehet. A múltban az optimalizáló nem észlelte, hogy ezek a fogási blokkok mind azonosak, ezért sok kódot duplikált az egyes ABI-k körül (ami hozzájárult ahhoz a meggyőződéshez, hogy a rendszerkód kivételeinek használata nagy bináris fájlokat eredményez). A Visual Studio 2019-től kezdődően azonban a C++ fordító összevonja az összes catch funcletet, és csak az egyedi példányokat tárolja. Ennek eredménye a kódméret további, összességében 18%-os csökkenése azon binárisoknál, amelyek nagymértékben támaszkodnak erre a mintára. Az EH-kód nemcsak hatékonyabb, mint a visszatérési kódok használata, hanem a nagyobb bináris fájlok miatti aggodalom is a múlté.
Növekményes buildfejlesztések
Az cppwinrt.exe eszköz most összehasonlítja a létrehozott fejléc/forrásfájl kimenetét a lemezen lévő meglévő fájlok tartalmával, és csak akkor írja ki a fájlt, ha a fájl valójában megváltozott. Ez jelentős időt takarít meg a lemez I/O-jával, és biztosítja, hogy a C++ fordító ne tekintse "piszkosnak" a fájlokat. Ennek az az eredménye, hogy az újrafordítás sok esetben elkerülhető vagy csökkenthető.
Az általános felületek most már mind létre lettek hozva
Az xlang metaadat-olvasója miatt a C++/WinRT mostantól minden paraméteres vagy általános felületet létrehoz a metaadatokból. Az olyan felületek, mint a Windows::Foundation::Collections::IVector<T>, most már metaadatokból jönnek létre, nem pedig kézzel írtak.winrt/base.h Az eredmény az, hogy a winrt/base.h mérete a felére csökkent, és az optimalizálások közvetlenül a kódban jönnek létre (amit a kézzel készített megközelítéssel nehéz volt megvalósítani).
Fontos
A megadott példában szereplőhöz hasonló felületek mostantól a megfelelő névtérfejlécekben jelennek meg, nem pedig a(z) winrt/base.h elemben. Ha tehát még nem tette meg, a felület használatához meg kell adnia a megfelelő névtérfejlécet.
Összetevők optimalizálása
Ez a frissítés több további, a C++/WinRT-hez készült opt-in optimalizálás támogatását is támogatja, az alábbi szakaszokban leírtak szerint. Mivel ezek az optimalizálások kompatibilitástörő változások (amelyek támogatásához előfordulhat, hogy kisebb módosításokat kell végrehajtania), kifejezetten be kell kapcsolnia őket. A Visual Studióban állítsa a projekt Common Properties>C++/WinRT>Optimized tulajdonságát Igen értékre. Ennek az a hatása, hogy hozzáadja a(z) <CppWinRTOptimized>true</CppWinRTOptimized> elemet a projektfájlhoz. És ugyanolyan hatással van, mint a -opt[imize] kapcsoló hozzáadása a parancssorból való cppwinrt.exe meghíváskor.
Alapértelmezés szerint egy új projekt (projektsablonból) lesz használva -opt .
Egységes építés és közvetlen megvalósítási hozzáférés
Ez a két optimalizálás lehetővé teszi, hogy az összetevő közvetlen hozzáférést biztosít a saját implementációs típusaihoz, még akkor is, ha csak a tervezett típusokat használja. Nincs szükség a make, make_self és get_self használatára, ha egyszerűen csak a nyilvános API-felületet szeretné használni. A hívásai közvetlenül az implementációba irányuló hívásokká fordulnak le, és ezek akár teljesen inline-olódhatnak is.
További információt és példakódokat az egységes építés és a közvetlen megvalósítási hozzáférés engedélyezése című témakörben talál.
Típustörlésű gyárak
Ez az optimalizálás elkerüli a #include függőségeket module.g.cpp , hogy ne kelljen minden alkalommal újrafordítást végrehajtani, amikor egyetlen implementációs osztály is megváltozik. Ennek eredménye a jobb buildteljesítmény.
Intelligensebb és hatékonyabb module.g.cpp a több libet tartalmazó nagy projektekhez
A module.g.cpp fájl két további, winrt_can_unload_now és winrt_get_activation_factory nevű összeírható segédet is tartalmaz. Ezeket olyan nagyobb projektekhez tervezték, amelyekben egy DLL több libből áll, amelyek mindegyike saját futtatókörnyezeti osztályokkal rendelkezik. Ebben a helyzetben kézzel kell összekapcsolnia a DLL DllGetActivationFactory és DllCanUnloadNow függvényeit. Ezek a segítők sokkal egyszerűbbé teszik ezt, mivel elkerülik a hamis eredethibákat. Az cppwinrt.exe eszköz -lib jelzője arra is használható, hogy minden egyes könyvtár saját preambulumot kapjon (a winrt_xxx helyett), így az egyes könyvtárak függvényei külön-külön elnevezhetők, és ezáltal egyértelműen kombinálhatók legyenek.
Korutin támogatása
A coroutine támogatása automatikusan megjelenik. Korábban a támogatás több helyen volt, ami túl korlátozónak tűnt. Ezután ideiglenesen a 2.0-s verzióhoz fejlécfájlra winrt/coroutine.h volt szükség, de erre már nincs szükség. Mivel a Windows-futtatókörnyezet aszinkron interfészeit most már generálják, nem pedig kézzel írják, ezért most már a winrt/Windows.Foundation.h alatt találhatók. Amellett, hogy karbantarthatóbb és könnyebben támogatható, azt is jelenti, hogy a korutinsegítőket, például a resume_foreground-ot, többé nem kell egy adott névtérfejléc végére hozzáfűzni. Ehelyett természetesebb módon belefoglalhatják a függőségeiket. Ez továbbá lehetővé teszi, hogy a resume_foreground ne csak egy adott Windows::UI::Core::CoreDispatcher esetén támogassa a folytatást, hanem mostantól egy adott Windows::System::DispatcherQueue esetén is. Korábban csak egy támogatott; de nem mindkettő, mivel a definíció csak egy névtérben található.
Íme egy példa a DispatcherQueue támogatására.
...
#include <winrt/Windows.System.h>
using namespace Windows::System;
...
fire_and_forget Async(DispatcherQueueController controller)
{
bool queued = co_await resume_foreground(controller.DispatcherQueue());
assert(queued);
// This is just to simulate queue failure...
co_await controller.ShutdownQueueAsync();
queued = co_await resume_foreground(controller.DispatcherQueue());
assert(!queued);
}
A korutinsegítők mostantól a [[nodiscard]] elemmel is el vannak látva, ami javítja a használhatóságukat. Ha elfelejti (vagy nem veszi észre, hogy kell) co_await őket ahhoz, hogy működjenek, akkor a(z) [[nodiscard]] miatt az ilyen hibák most fordítói figyelmeztetést eredményeznek.
Segítség a közvetlen (verem)foglalások diagnosztizálásához
Mivel a projekciós és az implementációs osztálynevek (alapértelmezés szerint) megegyeznek, és csak a névterük különbözik, könnyen összetéveszthetők, és véletlenül a veremen hozhat létre implementációt a make segédfüggvény-család használata helyett. Ez bizonyos esetekben nehéz lehet diagnosztizálni, mert az objektum megsemmisülhet, miközben a függőben lévő hivatkozások még mindig repülnek. Ezt most egy assert észleli a hibakeresési buildekben. Bár az állítás nem észleli a veremfoglalást egy koroutinban, mégis hasznos a legtöbb ilyen hiba észlelésében.
További információkért lásd: A közvetlen lefoglalások diagnosztizálása.
Továbbfejlesztett rögzítési segítők és variadikus meghatalmazottak
Ez a frissítés az előre jelzett típusok támogatásával is kijavítja a rögzítési segítők korlátozását. Ez időről időre felmerül a Windows-futtatókörnyezet interop API-knál, amikor azok egy leképezett típust adnak vissza.
Ez a frissítés get_strong ésget_weak is támogatja a variadikus (nem Windows-futtatókörnyezet) meghatalmazottak létrehozásakor.
A késleltetett megsemmisítés és a biztonságos QI támogatása a megsemmisítés során
Nem ritka, hogy egy futásidejű osztály objektumának destruktorában olyan metódust hívnak meg, amely ideiglenesen megnöveli a hivatkozásszámot. Amikor a referenciaszámláló újra nullára csökken, az objektum másodszor is megsemmisül. Az XAML-alkalmazásokban előfordulhat, hogy egy destruktorban el kell végeznie egy QueryInterface (QI) műveletet, hogy valamilyen karbantartási implementációt hívjon fel vagy le a hierarchiában. Az objektum hivatkozási száma azonban már elérte a nullát, így a QI is hivatkozásszám-visszapattanást jelent.
Ez a frissítés bevezeti a referenciaszám nullára csökkenésének biztonságos kezelését, biztosítva, hogy amint eléri a nullát, többé ne lehessen újra növelni; ugyanakkor továbbra is lehetővé teszi, hogy a megsemmisítés során QI-t hívjon meg az ideiglenesen szükséges interfészekhez. Ez az eljárás bizonyos XAML-alkalmazásokban/-vezérlőkben megkerülhetetlen, és a C++/WinRT mostantól ellenállóvá vált vele szemben.
Halaszthatja a megsemmisítést, ha statikus final_release függvényt ad meg a megvalósítási típushoz. Az objektumra mutató utolsó megmaradt mutató std::unique_ptr formájában kerül átadásra az Ön final_release függvényének. Ezután dönthet úgy, hogy a mutató tulajdonjogát más környezetbe helyezi át. Biztonságosan végezhet QI-hívást a mutatón anélkül, hogy kettős megsemmisítést idézne elő. Azonban a hivatkozásszám nettó változásának nullának kell lennie abban a pillanatban, amikor megsemmisíted az objektumot.
A final_release visszatérési értéke lehet voidaszinkron műveleti objektum, például IAsyncAction vagy winrt::fire_and_forget.
struct Sample : implements<Sample, IStringable>
{
hstring ToString()
{
return L"Sample";
}
~Sample()
{
// Called when the unique_ptr below is reset.
}
static void final_release(std::unique_ptr<Sample> self) noexcept
{
// Move 'self' as needed to delay destruction.
}
};
Az alábbi példában a MainPage kiadását követően (az utolsó alkalommal) final_release lesz meghívva. Ez a függvény öt másodpercig várakozik (a szálkészletben), majd az oldal Dispatcherét használva folytatódik (amihez a QI/AddRef/Release szükséges a működéshez). Ezután megtisztít egy erőforrást az adott felhasználói felületi szálon. Végül törli a unique_ptr, ami miatt a MainPage destruktort ténylegesen meghívják. Még ebben a destruktorban is meghívják a DataContextet , amely QI-t igényel az IFrameworkElementhez.
Nem kell a final_release koroutinként implementálnia. De ez működik, és nagyon egyszerűvé teszi a pusztítás áthelyezését egy másik szálra, ami ebben a példában történik.
struct MainPage : PageT<MainPage>
{
MainPage()
{
}
~MainPage()
{
DataContext(nullptr);
}
static IAsyncAction final_release(std::unique_ptr<MainPage> self)
{
co_await 5s;
co_await resume_foreground(self->Dispatcher());
co_await self->resource.CloseAsync();
// The object is destructed normally at the end of final_release,
// when the std::unique_ptr<MyClass> destructs. If you want to destruct
// the object earlier than that, then you can set *self* to `nullptr`.
self = nullptr;
}
};
További információ: Késleltetett megsemmisítés.
Továbbfejlesztett támogatás a COM-stílusú egyfelület-örökléshez
A Windows-futtatókörnyezet programozás mellett a C++/WinRT com-only API-k készítésére és felhasználására is használható. Ez a frissítés lehetővé teszi egy COM-kiszolgáló implementálását, ahol létezik interfészhierarchia. Ez nem szükséges a Windows-futtatókörnyezet, de bizonyos COM-implementációkhoz szükséges.
Paramok helyes kezelése out
Nehéz lehet paramokkal dolgozni, különösen Windows-futtatókörnyezet tömbökkelout. Ezzel a frissítéssel a C++/WinRT jelentősen robusztusabb és ellenállóbb a hibákkal szemben, ha paramokról és tömbökről van szó out ; függetlenül attól, hogy ezek a paraméterek nyelvi kivetítéssel érkeznek-e, vagy egy olyan COM-fejlesztőtől, aki a nyers ABI-t használja, és hibát követ el, hogy nem inicializálja a változókat következetesen. A C++/WinRT mindkét esetben helyesen jár el az ABI-nak előrejelzett típusok átadásakor (az erőforrások kiadásának megjegyzésével), valamint az ABI-n keresztül érkező paraméterek nullázása vagy törlésekor.
Az események mostantól megbízhatóan kezelik az érvénytelen tokeneket
A winrt::event implementáció mostantól elegánsan kezeli azt az esetet, amikor az eltávolítási metódus meghívása érvénytelen jogkivonat-értékkel történik (ez az érték nem szerepel a tömbben).
A koroutin helyi változói elpusztulnak, mielőtt a koroutin visszatér
A koroutin típus hagyományos implementálásának módja lehetővé teheti a koroutinon belüli helyi változók megsemmisítését a koroutin visszatérése/befejezése után (a végleges szuszpenzió előtt). A pincérek újrakezdését a végleges felfüggesztésig elhalasztják, hogy elkerüljék ezt a problémát, és egyéb előnyöket halmozhassanak fel.
Hírek és változások Windows SDK 10.0.17763.0-s verziójában (Windows 10, 1809-es verzió)
Az alábbi táblázat a C++/WinRT híreit és változásait tartalmazza a Windows SDK 10.0.17763.0-s verziójában (Windows 10, 1809-es verzió).
| Új vagy módosított funkció | További információk |
|---|---|
| Kompatibilitástörő változás. A fordításhoz a C++/WinRT nem függ a Windows SDK fejlécétől. | Lásd alább Windows SDK-fejlécfájlok elkülönítését. |
| A Visual Studio projektrendszer formátuma megváltozott. | Tekintse meg a C++/WinRT-projekt újrakonfigurálását a Windows SDK egy későbbi verziójára az alábbiakban. |
| Vannak új függvények és alaposztályok, amelyek segítenek átadni egy gyűjteményobjektumot egy Windows-futtatókörnyezet függvénynek, vagy saját gyűjteménytulajdonságokat és gyűjteménytípusokat implementálni. | Tekintse meg a C++/WinRT-lel rendelkező gyűjteményeket. |
| A {Binding} korrektúrakiterjesztést a C++/WinRT futtatókörnyezeti osztályokkal használhatja. | További információkért és példakódokért tekintse meg az adatkötés áttekintését. |
| A koroutin lemondásának támogatása lehetővé teszi a lemondási visszahívás regisztrálását. | További információ és példakód: Aszinkron művelet megszakítása és visszahívások lemondása. |
| Tagfüggvényre mutató delegált létrehozásakor a kezelő regisztrálásának pontján erős vagy gyenge hivatkozást hozhat létre az aktuális objektumhoz (nyers this mutató helyett). | További információkért és kódpéldákért lásd a A this mutató biztonságos elérése eseménykezelő delegátummal szakasz Tagfüggvény használata delegátumként című alszakaszát. |
| Kijavítottuk a hibákat, amelyeket Visual Studio A C++ szabványnak való jobb megfelelése derített fel. Az LLVM és a Clang eszközlánc is jobban használható a C++/WinRT szabványoknak való megfelelésének ellenőrzéséhez. | A jövőben már nem fog találkozni a(z) Miért nem fordul le az új projektem? Visual Studio 2017-et (15.8.0-s vagy újabb verzió) és 17134-es SDK-verziót használok című témakörben ismertetett problémával. |
Egyéb módosítások.
-
Kompatibilitástörő változás.
winrt::get_abi(winrt::hstring const>) most ad vissza
void*ahelyett, hogyHSTRING. Astatic_cast<HSTRING>(get_abi(my_hstring));használatával lekérhet egy HSTRINGet. Lásd: Az ABI HSTRING típusával való együttműködés. -
Kompatibilitástörő változás.
winrt::put_abi(winrt::hstring&) mostantól
void**ad visszaHSTRING*helyett. A(z)reinterpret_cast<HSTRING*>(put_abi(my_hstring));használatával lekérhet egy HSTRING*-t. Lásd: Az ABI HSTRING típusával való együttműködés. -
Kompatibilitástörő változás. A HRESULT mostantól winrt::hresult lesz. Ha HRESULT-ra van szüksége (a típusellenőrzéshez vagy a típustulajdonságok támogatásához), akkor
static_castparancsot is használhatja. Ellenkező esetben a winrt::hresult HRESULT-tá konvertálódik, feltéve, hogy azunknwn.helemet még azelőtt beilleszti, hogy bármilyen C++/WinRT-fejlécet felvenne. -
Kompatibilitástörő változás. A GUID mostantól winrt::guid néven van kivetítve. Az Ön által implementált API-k esetében a GUID-paraméterekhez a winrt::guid típust kell használnia. Ellenkező esetben a winrt::guid GUID-dé konvertálódik, feltéve, hogy a C++/WinRT-fejlécek beillesztése előtt beilleszti a(z)
unknwn.helemet. Lásd: Együttműködés az ABI GUID-struktúrájával. - Kompatibilitástörő változás. A winrt::handle_type konstruktort explicitsé tették (most már nehezebb helytelen kódot írni vele). Ha nyers leíróértéket kell hozzárendelnie, hívja inkább a handle_type::attach függvényt .
-
Kompatibilitástörő változás. A WINRT_CanUnloadNow és WINRT_GetActivationFactory aláírása megváltozott. Ezeket a függvényeket egyáltalán nem szabad deklarálni. Ehelyett foglalja bele az
winrt/base.hfejlécet (amely automatikusan belekerül, ha a C++/WinRT Windows-névtérhez tartozó bármely fejlécfájlt belefoglalja), hogy e függvények deklarációi is bekerüljenek. - A winrt::clock struktúra esetében a from_FILETIME/to_FILETIME a from_file_time/to_file_time javára elavultnak számítanak.
- Egyszerűsített API-k, amelyek IBuffer-paramétereket várnak. A legtöbb API a gyűjteményeket vagy tömböket részesíti előnyben. De úgy éreztük, hogy egyszerűbbé kell tenni az IBufferre támaszkodó API-k meghívását. Ez a frissítés közvetlen hozzáférést biztosít az IBuffer-implementáció mögötti adatokhoz. Ugyanazt az adatelnevezési konvenciót használja, mint amelyet a C++ standard kódtár-tárolók használnak. Ez a konvenció a hagyományosan nagybetűvel kezdődő metaadat-névvel való ütközést is elkerüli.
- Továbbfejlesztett kódlétrehozás: különböző fejlesztések a kódméret csökkentéséhez, a kódolás javításához és a gyári gyorsítótárazás optimalizálásához.
- Eltávolítva a szükségtelen rekurziót. Ha a parancssor egy mappára hivatkozik egy adott
.winmdhelyett, azcppwinrt.exeeszköz már nem keres rekurzívan.winmdfájlokat. Azcppwinrt.exeeszköz mostantól intelligensebben kezeli az ismétlődéseket, így rugalmasabbá válik a felhasználói hibákkal és a rosszul formázott.winmdfájlokkal szemben. - Edzett intelligens mutatók. Korábban az esemény-visszavonók nem vonták vissza az új érték áthelyezésekor. Ez segített feltárni azt a problémát, amely miatt az intelligens mutatóosztályok nem kezelték megbízhatóan az önkiosztást; a winrt::com_ptr struct sablonban gyökerezik. A winrt::com_ptr-t javították, és az esemény-visszavonó objektumokat úgy módosították, hogy helyesen kezeljék az áthelyezési szemantikát, így hozzárendeléskor visszavonódnak.
Fontos
Fontos módosítások történtek a C++/WinRT Visual Studio bővítményen (VSIX) mind az 1.0.181002.2-es, majd az 1.0.190128.4-es verzióban. A módosítások részleteiről, valamint arról, hogy ezek hogyan érintik a meglévő projekteket, lásd: A C++/WinRT Visual Studio-támogatása és A VSIX-bővítmény korábbi verziói.
Elkülönítés Windows SDK-fejlécfájloktól
Ez potenciálisan kompatibilitástörő változás lehet a kódod számára.
A fordításhoz a C++/WinRT már nem függ a Windows SDK fejlécfájljaitól. A C futásidejű kódtár (CRT) és a C++ Standard sablontár (STL) fejlécfájljai szintén nem tartalmaznak Windows SDK-fejléceket. Ez javítja a szabványoknak való megfelelőséget, elkerüli a véletlen függőségeket, és jelentősen csökkenti azoknak a makróknak a számát, amelyekkel szemben védelemre van szüksége.
Ez a függetlenség azt jelenti, hogy a C++/WinRT mostantól hordozhatóbb és szabványnak megfelelőbb, és tovább fejleszti annak lehetőségét, hogy több fordítóból és platformfüggetlen könyvtárból váljon. Ez azt is jelenti, hogy a makrók nincsenek hátrányos hatással a C++/WinRT fejlécekre.
Ha korábban a C++/WinRT-re bízta, hogy beillessze a Windows-fejléceket a projektjébe, akkor mostantól önnek kell ezeket beillesztenie. Mindenesetre mindig bevált gyakorlat explicit módon felvenni azokat a fejlécfájlokat, amelyekre támaszkodik, és nem egy másik könyvtárra bízni, hogy az Ön helyett foglalja be őket.
Jelenleg a Windows SDK-fejlécfájl elkülönítésének egyetlen kivétele a belső elemek és a numerikus elemek. Az utolsó fennmaradó függőségekkel kapcsolatban nincsenek ismert problémák.
A projektben szükség esetén újra engedélyezheti a Windows SDK-fejlécekkel való interopálást. Előfordulhat például, hogy egy COM-felületet szeretne implementálni (az IUnknownben gyökerezik). Ebben a példában vegye fel a(z) unknwn.h elemet, mielőtt bármilyen C++/WinRT fejlécet felvenne. Ennek hatására a C++/WinRT alapkönyvtár lehetővé teszi a különböző horgok használatát a klasszikus COM-felületek támogatásához. Kódpéldát lásd: COM-összetevők írása C++/WinRT használatával. Hasonlóképpen, explicit módon tartalmazzon minden más Windows SDK-fejlécet, amely deklarálja a meghívni kívánt típusokat és/vagy függvényeket.
Hogyan irányíthatja át a C++/WinRT-projektjét a Windows SDK egy újabb verziójára
A projekt újraépítésének módszere, amely valószínűleg a legkevesebb fordító- és linkerproblémát eredményezi, szintén a leginkább munkaigényes. Ez a módszer magában foglalja egy új projekt létrehozását (a választott Windows SDK-verziót célozza), majd a fájlokat átmásolja az új projektbe a régiből. A régi .vcxproj- és .vcxproj.filters-fájloknak lesznek olyan részei, amelyeket egyszerűen átmásolhat, így nem kell a fájlokat a Visual Studióban hozzáadnia.
Azonban a projekt célplatformjának módosítására két másik lehetőség is van a Visual Studio-ban.
- Lépjen az Általános>Windows SDK-verzió projekttulajdonságra, és válassza az Összes konfiguráció és minden platform lehetőséget. Állítsa Windows SDK-verziót a megcélzni kívánt verzióra.
- A Megoldáskezelő kattintson a jobb gombbal a projektcsomópontra, kattintson a Projektek újraépítése elemre, válassza ki a megcélzott verzió(ka)t, majd kattintson az OK gombra.
Ha a két módszer valamelyikének használata után fordító- vagy linkelőhibát tapasztal, próbálja meg megtisztítani a megoldást (aTiszta megoldás> és/vagy az összes ideiglenes mappa és fájl manuális törlése) a buildelés előtt.
Ha a C++ fordító a "C2039: "IUnknown" hibát állítja elő: nem tagja a "globális névtérnek", akkor adja hozzá #include <unknwn.h> a pch.h fájl elejéhez (mielőtt c++/WinRT-fejléceket használna).
Előfordulhat, hogy ezt követően is hozzá kell adnia #include <hstring.h> .
Ha a C++ linker a következő hibaüzenetet adja: "error LNK2019: unresolved external symbol _WINRT_CanUnloadNow@0 referenced in function _VSDesignerCanUnloadNow@0", akkor ezt úgy oldhatja meg, hogy hozzáadja a #define _VSDESIGNER_DONT_LOAD_AS_DLL elemet a(z) pch.h fájlhoz.
Windows developer