{"id":24906,"date":"2019-09-10T14:18:56","date_gmt":"2019-09-10T14:18:56","guid":{"rendered":"https:\/\/devblogs.microsoft.com\/cppblog\/?p=24906"},"modified":"2019-09-10T14:18:56","modified_gmt":"2019-09-10T14:18:56","slug":"c20-concepts-are-here-in-visual-studio-2019-version-16-3","status":"publish","type":"post","link":"https:\/\/devblogs.microsoft.com\/cppblog\/c20-concepts-are-here-in-visual-studio-2019-version-16-3\/","title":{"rendered":"C++20 Concepts Are Here in Visual Studio 2019 version 16.3"},"content":{"rendered":"<p><span data-contrast=\"auto\">C++20 Concepts are now supported for the first time in <\/span><a href=\"https:\/\/devblogs.microsoft.com\/visualstudio\/visual-studio-2019-version-16-3-preview-2-and-visual-studio-for-mac-version-8-3-preview-2-released\/\"><span data-contrast=\"none\">Visual Studio 2019 version 16.3 Preview 2<\/span><\/a><span data-contrast=\"auto\">. This includes both the compiler and standard library support. <\/span><\/p>\n<p><span data-contrast=\"auto\">First, we&#8217;re debuting the feature via \/<\/span><span data-contrast=\"auto\">std:c<\/span><span data-contrast=\"auto\">++latest mode and once we have all C++20 features implemented across all Visual Studio products (compiler, library, IntelliSense, build system, debugger, <\/span><span data-contrast=\"auto\">etc<\/span><span data-contrast=\"auto\">.<\/span><span data-contrast=\"auto\">), we&#8217;ll provide them through a new \/<\/span><span data-contrast=\"auto\">std:c<\/span><span data-contrast=\"auto\">++20 mode.<\/span><span data-ccp-props=\"{&quot;201341983&quot;:0,&quot;335559731&quot;:720,&quot;335559739&quot;:160,&quot;335559740&quot;:259}\"> IntelliSense support is not currently available and our implementation doesn\u2019t yet include recent changes in the ISO C++ standards meeting in Cologne.\u00a0<\/span><\/p>\n<h3>What are C++ Concepts?<\/h3>\n<p>Concepts are predicates that you use to express a generic algorithm\u2019s expectations on its template arguments.<\/p>\n<p>Concepts allow you to formally document constraints on templates and have the compiler enforce them. As a bonus, you can also take advantage of that enforcement to improve the compile time of your program via concept-based overloading.<\/p>\n<p>There are many useful resources about Concepts on the Internet. For example, <a href=\"https:\/\/isocpp.org\/blog\/tag\/concepts\">isocpp<\/a> has many blog posts about Concepts which include one from <a href=\"https:\/\/isocpp.org\/blog\/2016\/02\/a-bit-of-background-for-concepts-and-cpp17-bjarne-stroustrup\">Bjarne Stroustrup<\/a>.<\/p>\n<h3>What is supported?<\/h3>\n<p><span data-contrast=\"auto\">The compiler support includes<\/span><span data-contrast=\"auto\">:<\/span><span data-ccp-props=\"{&quot;201341983&quot;:0,&quot;335559739&quot;:160,&quot;335559740&quot;:259}\">\u00a0<\/span><\/p>\n<ul>\n<li><a href=\"https:\/\/wg21.link\/p0734r0\"><span data-contrast=\"none\">P0734R0: Wording Paper, C++ extensions for Concepts<\/span><\/a><span data-ccp-props=\"{&quot;201341983&quot;:0,&quot;335559731&quot;:720,&quot;335559739&quot;:160,&quot;335559740&quot;:259}\">\u00a0<\/span>\n<ul>\n<li><span data-contrast=\"none\">Also pat<\/span><span data-contrast=\"none\">c<\/span><span data-contrast=\"none\">hed by wording changes from <\/span><a href=\"https:\/\/wg21.link\/p1141r2\"><span data-contrast=\"none\">P1141R2: Yet another approach for constrained declarations<\/span><\/a><span data-contrast=\"none\">, but doesn&#8217;t include abbreviated function templates and placeholder-type-specifier with type constraint.<\/span><span data-ccp-props=\"{&quot;201341983&quot;:0,&quot;335551550&quot;:1,&quot;335551620&quot;:1,&quot;335559685&quot;:360,&quot;335559739&quot;:160,&quot;335559740&quot;:259}\">\u00a0<\/span><\/li>\n<\/ul>\n<\/li>\n<li><a href=\"https:\/\/wg21.link\/p0857r0\"><span data-contrast=\"none\">P0857R0: Wording for \u201cfunctionality gaps in constraints\u201d<\/span><\/a><span data-ccp-props=\"{&quot;201341983&quot;:0,&quot;335559731&quot;:720,&quot;335559739&quot;:160,&quot;335559740&quot;:259}\">\u00a0<\/span><\/li>\n<li><a href=\"https:\/\/wg21.link\/p1084r2\"><span data-contrast=\"none\">P1084R2: Today\u2019s return-type-requirements Are Insuf\ufb01cient<\/span><\/a><span data-ccp-props=\"{&quot;201341983&quot;:0,&quot;335559731&quot;:720,&quot;335559739&quot;:160,&quot;335559740&quot;:259}\">\u00a0<\/span><\/li>\n<li><a href=\"https:\/\/wg21.link\/p0717R1\"><span data-contrast=\"none\">P0717R1<\/span><span data-contrast=\"none\">: Semantic constraint matching for concepts<\/span><\/a><span data-ccp-props=\"{&quot;201341983&quot;:0,&quot;335551550&quot;:1,&quot;335551620&quot;:1,&quot;335559731&quot;:720,&quot;335559739&quot;:160,&quot;335559740&quot;:259}\">\u00a0<\/span><\/li>\n<\/ul>\n<p><span data-contrast=\"none\">The compiler support doesn\u2019t include recent changes in the ISO C++ standards meeting in Cologne.<\/span><span data-ccp-props=\"{&quot;201341983&quot;:0,&quot;335551550&quot;:1,&quot;335551620&quot;:1,&quot;335559739&quot;:160,&quot;335559740&quot;:259}\">\u00a0<\/span><\/p>\n<p><span data-contrast=\"auto\">The library support includes: <\/span><a href=\"http:\/\/wg21.link\/P0898R3\"><span data-contrast=\"none\">&lt;concepts&gt;<\/span><\/a><\/p>\n<h3>Examples<\/h3>\n<p><span data-contrast=\"auto\">Here <\/span><span data-contrast=\"auto\">are some<\/span><span data-contrast=\"auto\"> example<\/span><span data-contrast=\"auto\">s<\/span><span data-contrast=\"auto\"> on how Concepts can help you write more concise code. They also take less time to compile.<\/span><\/p>\n<pre class=\"lang:c++ decode:true\">#include &lt;concepts&gt;\r\n\r\n\/\/ This concept tests whether 'T::type' is a valid type\r\ntemplate&lt;typename T&gt;\r\nconcept has_type_member = requires { typename T::type; };\r\n\r\nstruct S1 {};\r\nstruct S2 { using type = int; };\r\n\r\nstatic_assert(!has_type_member&lt;S1&gt;);\r\nstatic_assert(has_type_member&lt;S2&gt;);\r\n\r\n\/\/ Currently, MSVC doesn't support requires-expressions everywhere; they only work in concept definitions and in requires-clauses\r\n\/\/template &lt;class T&gt; constexpr bool has_type_member_f(T) { return requires{ typename T::type; }; }\r\ntemplate &lt;class T&gt; constexpr bool has_type_member_f(T) { return has_type_member&lt;T&gt;; }\r\n\r\nstatic_assert(!has_type_member_f(S1{}));\r\nstatic_assert(has_type_member_f(S2{}));\r\n\r\n\/\/ This concept tests whether 'T::value' is a valid expression which can be implicitly converted to bool\r\n\/\/ 'std::convertible_to' is a concept defined in &lt;concepts&gt;\r\ntemplate&lt;typename T&gt;\r\nconcept has_bool_value_member = requires { { T::value } -&gt; std::convertible_to&lt;bool&gt;; };\r\n\r\nstruct S3 {};\r\nstruct S4 { static constexpr bool value = true; };\r\nstruct S5 { static constexpr S3 value{}; };\r\n\r\nstatic_assert(!has_bool_value_member&lt;S3&gt;);\r\nstatic_assert(has_bool_value_member&lt;S4&gt;);\r\nstatic_assert(!has_bool_value_member&lt;S5&gt;);\r\n\r\n\/\/ The function is only a viable candidate if 'T::value' is a valid expression which can be implicitly converted to bool\r\ntemplate&lt;has_bool_value_member T&gt;\r\nbool get_value()\r\n{\r\n\treturn T::value;\r\n}\r\n\r\n\/\/ This concept tests whether 't + u' is a valid expression\r\ntemplate&lt;typename T, typename U&gt;\r\nconcept can_add = requires(T t, U u) { t + u; };\r\n\r\n\/\/ The function is only a viable candidate if 't + u' is a valid expression\r\ntemplate&lt;typename T, typename U&gt; requires can_add&lt;T, U&gt;\r\nauto add(T t, U u)\r\n{\r\n\treturn t + u;\r\n}\r\n<\/pre>\n<h3>What about ranges?<\/h3>\n<p>We are also working on <a href=\"https:\/\/wg21.link\/p0896r4\">ranges<\/a>. It <span class=\"TextRun SCXW155793071 BCX1\" lang=\"EN-US\" xml:lang=\"EN-US\" data-contrast=\"none\"><span class=\"NormalTextRun SCXW155793071 BCX1\">provides components for dealing with ranges of <\/span><span class=\"ContextualSpellingAndGrammarError SCXW155793071 BCX1\">element<\/span><\/span><span class=\"TextRun SCXW155793071 BCX1\" lang=\"EN-US\" xml:lang=\"EN-US\" data-contrast=\"none\"><span class=\"NormalTextRun SCXW155793071 BCX1\"> and has a <\/span><span class=\"ContextualSpellingAndGrammarError SCXW155793071 BCX1\">tight<\/span><span class=\"NormalTextRun SCXW155793071 BCX1\"> relationship with Concepts<\/span><\/span><span class=\"TextRun SCXW155793071 BCX1\" lang=\"EN-US\" xml:lang=\"EN-US\" data-contrast=\"none\"><span class=\"NormalTextRun SCXW155793071 BCX1\">.<\/span><\/span><\/p>\n<p>In the meantime, we used the reference implementation<span data-contrast=\"auto\">\u00a0<\/span><a href=\"https:\/\/github.com\/ericniebler\/range-v3\"><span data-contrast=\"none\">range-v3<\/span><\/a><span data-contrast=\"auto\"> and <\/span><a href=\"https:\/\/github.com\/CaseyCarter\/cmcstl2\"><span data-contrast=\"none\">cmcstl2<\/span><\/a><span data-contrast=\"auto\"> to test the Concepts support and they helped discover many <\/span><span data-contrast=\"auto\">issues<\/span><span data-contrast=\"auto\">.<\/span> <span data-contrast=\"auto\">S<\/span><span data-contrast=\"auto\">ome<\/span><span data-contrast=\"auto\"> are related <\/span><span data-contrast=\"auto\">to <\/span><span data-contrast=\"auto\">the <\/span><span data-contrast=\"auto\">C<\/span><span data-contrast=\"auto\">oncept<\/span><span data-contrast=\"auto\">s<\/span> <span data-contrast=\"auto\">implementation and<\/span><span data-contrast=\"auto\"> some are issues in other feature areas which are exposed by the new coding pattern enabled by <\/span><span data-contrast=\"auto\">C<\/span><span data-contrast=\"auto\">oncept<\/span><span data-contrast=\"auto\">s<\/span><span data-contrast=\"auto\">.<\/span><span data-contrast=\"auto\"> We fixed all issues in the first category and fixed most of the issues in the second category (the remaining issues are worked around in the source). We now <\/span><span data-contrast=\"auto\">compile <\/span><span data-contrast=\"auto\">and run all the tests in these libr<\/span><span data-contrast=\"auto\">aries <\/span><span data-contrast=\"auto\">during<\/span><span data-contrast=\"auto\"> our CI (continuous integration)<\/span><span data-contrast=\"auto\">.<\/span><\/p>\n<p><span data-contrast=\"none\">The testing also helped expose some source issues in the reference implementation and we reported them to the library owner.<\/span><span data-ccp-props=\"{&quot;201341983&quot;:0,&quot;335551550&quot;:1,&quot;335551620&quot;:1,&quot;335559739&quot;:160,&quot;335559740&quot;:259}\">\u00a0<\/span><\/p>\n<h3>Looking for libraries using C++20 features<\/h3>\n<p><span data-contrast=\"none\">Like many other new features we implemented recently, Concepts also use <\/span><span data-contrast=\"none\">the new <\/span><a href=\"https:\/\/devblogs.microsoft.com\/cppblog\/rejuvenating-the-microsoft-cc-compiler\/\"><span data-contrast=\"none\">p<\/span><span data-contrast=\"none\">arser and semantics analysis actions<\/span><\/a><span data-contrast=\"none\">. <\/span><span data-contrast=\"none\">While they <\/span><span data-contrast=\"none\">have a pretty good coverage<\/span><span data-contrast=\"none\"> and we have confidence in the quality<\/span><span data-contrast=\"none\">, experience shows that we s<\/span><span data-contrast=\"none\">till s<\/span><span data-contrast=\"none\">ometimes see issues<\/span><span data-contrast=\"none\"> especially when people start to adopt new coding patterns enabled by the new features.<\/span><span data-ccp-props=\"{&quot;201341983&quot;:0,&quot;335551550&quot;:1,&quot;335551620&quot;:1,&quot;335559739&quot;:160,&quot;335559740&quot;:259}\">\u00a0<\/span><\/p>\n<p><span data-contrast=\"auto\">We are always looking for libraries which have heavy usage of new features. If you have some libraries which use <\/span><span data-contrast=\"auto\">Concepts or other C++20 features,<\/span><span data-contrast=\"auto\"> please let us know and we <\/span><span data-contrast=\"auto\">are willing to add them to our daily RWC (real world code) testing<\/span><span data-contrast=\"auto\">.<\/span><span data-contrast=\"auto\"> This will help us improve our compiler.<\/span><span data-ccp-props=\"{&quot;201341983&quot;:0,&quot;335559731&quot;:720,&quot;335559739&quot;:160,&quot;335559740&quot;:259}\">\u00a0<\/span><\/p>\n<h3>Talk to us!<\/h3>\n<p><span data-contrast=\"auto\">If you have feedback on the C++20 Concepts support in Visual Studio, we would love to hear from you. We can be reached via the comments below. <\/span><span data-contrast=\"auto\">Y<\/span><span data-contrast=\"auto\">ou can <\/span><span data-contrast=\"auto\">also <\/span><span data-contrast=\"auto\">use the <\/span><a href=\"https:\/\/docs.microsoft.com\/en-us\/visualstudio\/ide\/how-to-report-a-problem-with-visual-studio?view=vs-2019\"><span data-contrast=\"none\">Report a Problem<\/span><\/a><span data-contrast=\"auto\"> tool in Visual Studio or head over to <\/span><a href=\"https:\/\/developercommunity.visualstudio.com\/spaces\/62\/index.html\"><span data-contrast=\"none\">Visual Studio Developer Community<\/span><\/a><span data-contrast=\"auto\">. You can also find us on Twitter <\/span><a href=\"https:\/\/twitter.com\/visualc\"><span data-contrast=\"none\">@VisualC<\/span><\/a><span data-contrast=\"auto\">.<\/span><span data-ccp-props=\"{&quot;201341983&quot;:0,&quot;335559731&quot;:720,&quot;335559739&quot;:160,&quot;335559740&quot;:259}\">\u00a0<\/span><\/p>\n","protected":false},"excerpt":{"rendered":"<p>C++20 Concepts are now available for the first time in Visual Studio 2019 version 16.3 Preview 2. This includes both the compiler and standard library support, but not the intellisense support.<\/p>\n","protected":false},"author":6968,"featured_media":24965,"comment_status":"open","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"footnotes":""},"categories":[270],"tags":[],"class_list":["post-24906","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-announcement"],"acf":[],"blog_post_summary":"<p>C++20 Concepts are now available for the first time in Visual Studio 2019 version 16.3 Preview 2. This includes both the compiler and standard library support, but not the intellisense support.<\/p>\n","_links":{"self":[{"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/posts\/24906","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/users\/6968"}],"replies":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/comments?post=24906"}],"version-history":[{"count":0,"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/posts\/24906\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/media\/24965"}],"wp:attachment":[{"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/media?parent=24906"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/categories?post=24906"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/devblogs.microsoft.com\/cppblog\/wp-json\/wp\/v2\/tags?post=24906"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}