{"id":1929,"date":"2014-10-15T16:34:34","date_gmt":"2014-10-15T14:34:34","guid":{"rendered":"http:\/\/mariusbancila.ro\/blog\/?p=1929"},"modified":"2014-10-20T15:03:32","modified_gmt":"2014-10-20T13:03:32","slug":"extension-methods-in-cpp","status":"publish","type":"post","link":"https:\/\/mariusbancila.ro\/blog\/2014\/10\/15\/extension-methods-in-cpp\/","title":{"rendered":"Extension methods in C++"},"content":{"rendered":"<p>A few days ago Bjarne Stroustrup has published a proposal paper (<a href=\"http:\/\/www.open-std.org\/jtc1\/sc22\/wg21\/docs\/papers\/2014\/n4174.pdf\">N4174<\/a>) to the C++ standard committee called <em>Call syntax: x.f(y) vs. f(x,y)<\/em>. The following excerpt from the paper summarizes the proposal:<\/p>\n<blockquote><p>The basic suggestion is to define <strong>x.f(y)<\/strong> and <strong>f(x,y)<\/strong> to be equivalent. In addition, to increase compatibility and modularity, I suggest we explore the possibility of ignoring uncallable and inaccessible members when looking for a member function (or function object) to call.<\/p>\n<p><strong>x.f(y)<\/strong> means<\/p>\n<ol>\n<li>First try x.f(y) \u2013does x\u2019s class have a member f? If so try to use it<\/li>\n<li>Then try f(x,y) \u2013 is there a function f? If so, try to use it<\/li>\n<li>otherwise error<\/li>\n<\/ol>\n<p><strong>f(x,y)<\/strong> means<\/p>\n<ol>\n<li>First try x.f(y) \u2013 does x\u2019s class have a member f? If so try to use it<\/li>\n<li>First try f(x,y) \u2013 is there a function f? If so, try to use it<\/li>\n<li>otherwise error<\/li>\n<\/ol>\n<\/blockquote>\n<p>This may sound a bit crazy, but to me this immediately shouted EXTENSION METHODS, which is something that I&#8217;ve been wondering for a while how could be added to the language. I find this one of the most important proposals (I am aware of) for the evolution of the C++ language.<\/p>\n<p><strong>UPDATE<\/strong>: Recently I have discovered that a second paper on the same topic exists. The <a href=\"http:\/\/www.open-std.org\/jtc1\/sc22\/wg21\/docs\/papers\/2014\/n4165.pdf\">N4165<\/a> paper, called <strong>Unified Call Syntax<\/strong>, is authored by Herb Sutter. Unlike the first paper, Sutter&#8217;s paper proposes only making x.f(y) equivalent to f(x,y) and not the other way around. Here is a quote from the paper:<\/p>\n<blockquote><p>\nThis single proposal aims to address two major issues:<\/p>\n<ul>\n<li><em>Enable more-generic code<\/em>: Today, generic code cannot invoke a function on a T object without knowing whether the function is a member or nonmember, and must commit to one. This is long-standing known issue in C++.<\/li>\n<li><em>Enable &#8220;extension methods&#8221; without a separate one-off language feature<\/em>: The proposed generalization enables calling nonmember functions (and function pointers, function objects, etc.) symmetrically with member functions, but without a separate and more limited &#8220;extension methods&#8221; language feature. Further, unlike &#8220;extension methods&#8221; in other languages which are a special-purpose feature that adds only the ability to add member functions to an existing class, this pro-posal would immediately work with calling existing library code without any change. (See also following points.)<\/li>\n<\/ul>\n<\/blockquote>\n<p>Herb Sutter argues that the unified call syntax would achieve major benefits including consistency, simplicity, and teachability, improve of discoverability and usability of existing code and improve C++ tool support. However, he also explains why why making f(x) equivalent to x.f() is not possible since it would break existing code.<\/p>\n<h2>Extension Methods in C#<\/h2>\n<p>I&#8217;ll take a step back for a short paragraph on extension methods in C#. <\/p>\n<p>An extension method allows you to add functionality to an existing type without modifying the original type or creating a derived type (and without needing to recompile the code containing the type that is extended.)<\/p>\n<p>Let&#8217;s assume you want to write a method that counts words in a text. You could write a method called <tt>WordCount<\/tt> that looks like this (for simplicity we&#8217;ll only consider space as a delimiter):<\/p>\n<pre class=\"lang:c# decode:true \" >static class StringUtilities\r\n{\r\n   public static int WordCount(string text)\r\n   {\r\n      return text.Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries).Length;\r\n   }\r\n}<\/pre>\n<p>You can use it like this:<\/p>\n<pre class=\"lang:c# decode:true \" >\r\nvar text = \"This is an example\";\r\nvar count = WordCount(text);\r\n<\/pre>\n<p>Just by changing the syntax a bit and adding the <tt>this<\/tt> keyword in front of the type of first argument (always the type you want to extend), the compiler treats the method as part of the type.<\/p>\n<pre class=\"lang:c# decode:true \" >\r\nstatic class StringUtilities\r\n{\r\n   public static int WordCount(this string text)\r\n   {\r\n      return text.Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries).Length;\r\n   }\r\n}<\/pre>\n<p>With this change we can now write:<\/p>\n<pre class=\"lang:c# decode:true \" >\r\nvar text = \"This is an example\";\r\nvar count = text.WordCount();\r\n<\/pre>\n<p><tt>WordCount(text)<\/tt> vs. <tt>text.WordCount()<\/tt> is exactly what the Stroustrup&#8217;s N4174 paper is proposing.<\/p>\n<p>Notice the extension methods in C# have several requirements including the following:<\/p>\n<ul>\n<li>the extension method is always a public static member of a static class<\/li>\n<li>the extension method has access only to the public interface of the extended type<\/li>\n<\/ul>\n<h2>Extension Methods in C++<\/h2>\n<p>The question that one may ask is how would this equivalence of <strong>x.f(y)<\/strong> and <strong>f(x,y)<\/strong> be beneficial to the language. My immediate answer is that it defines extension methods and enable developers to extend functionality without touching exiting code. <\/p>\n<p>Let&#8217;s take a real case example. The C++ standard containers provide methods like <tt>find()<\/tt> to find an element in the container. There are also generic algorithms for the same purpose (that work in a generic way for various ranges defined by iterators). But this <tt>find()<\/tt> methods return an iterator and you have to check the value against the <tt>end()<\/tt> to interpret the result. Using <tt>std::map<\/tt> for instance, many times you just need to know whether it contains a key or not. <tt>std::map<\/tt> does not have a <tt>contains()<\/tt> method, but you can easily write a helper function:<\/p>\n<pre class=\"lang:default decode:true \" >template&lt;typename TKey, typename TValue&gt;\r\nbool contains(std::map&lt;TKey, TValue&gt; const &amp; c, TKey const key)\r\n{\r\n   return c.find(key) != c.end();\r\n}\r\n<\/pre>\n<p>And with that in place you can write:<\/p>\n<pre class=\"lang:default decode:true \" >\r\nauto m = std::map&lt;int, char&gt; {{1, 'a'}, {2, 'b'}, {3,'c'}};\r\nif(contains(m, 1))\r\n{\r\n   std::cout &lt;&lt; \"key exists\" &lt;&lt; std::endl;\r\n}\r\n<\/pre>\n<p>However, I would very much like to be able to say (because in an object oriented world this seems much more natural to me):<\/p>\n<pre class=\"lang:default decode:true \" >\r\nif(m.contains(1))\r\n{\r\n}\r\n<\/pre>\n<p>If <strong>x.f(y)<\/strong> and <strong>f(x,y)<\/strong> were equivalent this later code would be perfectly legal (and beautiful).<\/p>\n<p>Here is a second example. Suppose you want to define some query operators like the ones available in LINQ in .NET. Below is a dummy implementation of several such operators for <tt>std::vector<\/tt>.<\/p>\n<pre class=\"lang:default decode:true \" >template&lt;typename T, typename UnaryPredicate&gt;\r\nstd::vector&lt;T&gt; where(std::vector&lt;T&gt; const &amp; c, UnaryPredicate predicate)\r\n{\r\n   std::vector&lt;T&gt; v;\r\n   std::copy_if(std::begin(c), std::end(c), std::back_inserter(v), predicate);\r\n   return v;\r\n}\r\n\r\ntemplate &lt;typename T, typename F, typename R = typename std::result_of&lt;F(T)&gt;::type&gt;\r\nstd::vector&lt;R&gt; select(std::vector&lt;T&gt; const &amp; c, F s)\r\n{\r\n   std::vector&lt;R&gt; v;\r\n   std::transform(std::begin(c), std::end(c), std::back_inserter(v), s);\r\n   return v;\r\n}\r\n\r\ntemplate&lt;typename T&gt;\r\nT sum(std::vector&lt;T&gt; const &amp; c)\r\n{\r\n   return std::accumulate(std::begin(c), std::end(c), 0);\r\n}<\/pre>\n<p>(Many thanks to <a href=\"http:\/\/stackoverflow.com\/users\/3953764\/piotr-s\">Piotr S.<\/a> and <a href=\"http:\/\/stackoverflow.com\/users\/1774667\/yakk\">Yakk<\/a> for <a href=\"http:\/\/stackoverflow.com\/questions\/26383517\/template-projection-function-cannot-deduce-type-arguments\">helping with the implementation<\/a> of <tt>select<\/tt>.)<\/p>\n<p>Those functions enable us to write code that &#8220;sums the square of the even numbers from a range&#8221; as shown below:<\/p>\n<pre class=\"lang:default decode:true \" >\r\nauto v = std::vector&lt;int&gt; {1,2,3,4,5,6,7,8,9};\r\n\r\nauto t1 = where(v, [](int e){return e % 2 == 0; });\r\nauto t2 = select(t1, [](int e){return e*e; });\r\nauto s = sum(t2);\r\n<\/pre>\n<p>I don&#8217;t particularly like how the code looks. You have to catch the return value from each function even though it&#8217;s an intermediary value that you discard later. <\/p>\n<p>One can improve that by using the return value from the previous call as a direct argument to the next call:<\/p>\n<pre class=\"lang:default decode:true \" >\r\nauto s = sum(select(where(v, [](int e){return e % 2 == 0; }), [](int e){return e*e; }));\r\n<\/pre>\n<p>However, I like this even less. First, because it gets hard to follow what are the arguments for each call (and even if you try to format it differently it&#8217;s not going to help much) and second because it inverses the natural reading order or the operations. You first see <tt>sum<\/tt>, then <tt>select<\/tt> and last <tt>where<\/tt>. Even though this is how we described it earlier (&#8220;sums the square of the even numbers from a range&#8221;), it is misleading with regard to the order of the operations.<\/p>\n<p>However, if <strong>x.f(y)<\/strong> and <strong>f(x,y)<\/strong> were equivalent it would be very easy to write the above code like this:<\/p>\n<pre class=\"lang:default decode:true \" >\r\nauto v = std::vector&lt;int&gt; {1,2,3,4,5,6,7,8,9};\r\nauto s = v.where([](int e){return e % 2 == 0; })\r\n          .select([](int e){return e*e; })\r\n          .sum();\r\n<\/pre>\n<p>Isn&#8217;t that beautiful? I think it is. <\/p>\n<h2>Conclusion<\/h2>\n<p>The <a href=\"http:\/\/www.open-std.org\/jtc1\/sc22\/wg21\/docs\/papers\/2014\/n4174.pdf\">N4174<\/a> paper is rather an exploration of possibilities for uniform calling syntax than a very formal proposal. There are various aspects that have to be carefully considered especially when considering how to treat <strong>f(x, y)<\/strong>. The <a href=\"http:\/\/www.open-std.org\/jtc1\/sc22\/wg21\/docs\/papers\/2014\/n4165.pdf\">N4165<\/a> paper makes a good case of the uniform calling syntax, explains the benefits better and argues against treating f(x) equivalent to x.f(). You should go ahead and read the two papers for detailed information. However, I sincerely hope that one day this will be accepted and become a core feature of the C++ language.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>A few days ago Bjarne Stroustrup has published a proposal paper (N4174) to the C++ standard committee called Call syntax: x.f(y) vs. f(x,y). The following excerpt from the paper summarizes the proposal: The basic suggestion is to define x.f(y) and f(x,y) to be equivalent. In addition, to increase compatibility and modularity, I suggest we explore &#8230; <a title=\"Extension methods in C++\" class=\"read-more\" href=\"https:\/\/mariusbancila.ro\/blog\/2014\/10\/15\/extension-methods-in-cpp\/\" aria-label=\"Read more about Extension methods in C++\">Read more<\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_uag_custom_page_level_css":"","advgb_blocks_editor_width":"","advgb_blocks_columns_visual_guide":"","_jetpack_newsletter_access":"","_jetpack_dont_email_post_to_subs":false,"_jetpack_newsletter_tier_id":0,"_jetpack_memberships_contains_paywalled_content":false,"_jetpack_feature_clip_id":0,"_jetpack_memberships_contains_paid_content":false,"footnotes":"","jetpack_publicize_message":"","jetpack_publicize_feature_enabled":true,"jetpack_social_post_already_shared":true,"jetpack_social_options":{"image_generator_settings":{"template":"highway","default_image_id":0,"font":"","enabled":false},"version":2},"jetpack_post_was_ever_published":false},"categories":[7],"tags":[451,427,428,74,429],"class_list":["post-1929","post","type-post","status-publish","format-standard","hentry","category-c","tag-c","tag-extension-methods","tag-n4174","tag-standard","tag-stroustrup"],"aioseo_notices":[],"aioseo_head":"\n\t\t<!-- All in One SEO 5.0.4 - aioseo.com -->\n\t<meta name=\"description\" content=\"This article explores the advantages of having extension methods in C++ as proposed in the N4174 paper by Bjarne Stroustrup.\" \/>\n\t<meta name=\"robots\" content=\"max-image-preview:large\" \/>\n\t<meta name=\"author\" content=\"Marius Bancila\"\/>\n\t<meta name=\"keywords\" content=\"c++,standard,extension methods,n4174,stroustrup\" \/>\n\t<link rel=\"canonical\" href=\"https:\/\/mariusbancila.ro\/blog\/2014\/10\/15\/extension-methods-in-cpp\/\" \/>\n\t\t<meta name=\"generator\" content=\"All in One SEO (AIOSEO) 5.0.4\" \/>\n\t\t<meta property=\"og:locale\" content=\"en_US\" \/>\n\t\t<meta property=\"og:site_name\" content=\"Marius Bancila&#039;s Blog | About code. Mostly on C++\" \/>\n\t\t<meta property=\"og:type\" content=\"article\" \/>\n\t\t<meta property=\"og:title\" content=\"Extension methods in C++\" \/>\n\t\t<meta property=\"og:description\" content=\"This article explores the advantages of having extension methods in C++ as proposed in the N4174 paper by Bjarne Stroustrup.\" \/>\n\t\t<meta property=\"og:url\" content=\"https:\/\/mariusbancila.ro\/blog\/2014\/10\/15\/extension-methods-in-cpp\/\" \/>\n\t\t<meta property=\"article:published_time\" content=\"2014-10-15T14:34:34+00:00\" \/>\n\t\t<meta property=\"article:modified_time\" content=\"2014-10-20T13:03:32+00:00\" \/>\n\t\t<meta name=\"twitter:card\" content=\"summary\" \/>\n\t\t<meta name=\"twitter:title\" content=\"Extension methods in C++\" \/>\n\t\t<meta name=\"twitter:description\" content=\"This article explores the advantages of having extension methods in C++ as proposed in the N4174 paper by Bjarne Stroustrup.\" \/>\n\t\t<script type=\"application\/ld+json\" class=\"aioseo-schema\">\n\t\t\t{\"@context\":\"https:\\\/\\\/schema.org\",\"@graph\":[{\"@type\":\"Article\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/2014\\\/10\\\/15\\\/extension-methods-in-cpp\\\/#article\",\"name\":\"Extension methods in C++\",\"headline\":\"Extension methods in C++\",\"author\":{\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/author\\\/admin\\\/#author\"},\"publisher\":{\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/#organization\"},\"datePublished\":\"2014-10-15T16:34:34+02:00\",\"dateModified\":\"2014-10-20T15:03:32+02:00\",\"inLanguage\":\"en-US\",\"commentCount\":10,\"mainEntityOfPage\":{\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/2014\\\/10\\\/15\\\/extension-methods-in-cpp\\\/#webpage\"},\"isPartOf\":{\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/2014\\\/10\\\/15\\\/extension-methods-in-cpp\\\/#webpage\"},\"articleSection\":\"C++, C++, extension methods, N4174, standard, Stroustrup\"},{\"@type\":\"BreadcrumbList\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/2014\\\/10\\\/15\\\/extension-methods-in-cpp\\\/#breadcrumblist\",\"itemListElement\":[{\"@type\":\"ListItem\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/#listItem\",\"position\":1,\"name\":\"Home\",\"item\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/\",\"nextItem\":{\"@type\":\"ListItem\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/category\\\/it\\\/#listItem\",\"name\":\"IT\"}},{\"@type\":\"ListItem\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/category\\\/it\\\/#listItem\",\"position\":2,\"name\":\"IT\",\"item\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/category\\\/it\\\/\",\"nextItem\":{\"@type\":\"ListItem\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/category\\\/it\\\/software\\\/#listItem\",\"name\":\"Software\"},\"previousItem\":{\"@type\":\"ListItem\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/#listItem\",\"name\":\"Home\"}},{\"@type\":\"ListItem\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/category\\\/it\\\/software\\\/#listItem\",\"position\":3,\"name\":\"Software\",\"item\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/category\\\/it\\\/software\\\/\",\"nextItem\":{\"@type\":\"ListItem\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/category\\\/it\\\/software\\\/c\\\/#listItem\",\"name\":\"C++\"},\"previousItem\":{\"@type\":\"ListItem\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/category\\\/it\\\/#listItem\",\"name\":\"IT\"}},{\"@type\":\"ListItem\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/category\\\/it\\\/software\\\/c\\\/#listItem\",\"position\":4,\"name\":\"C++\",\"item\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/category\\\/it\\\/software\\\/c\\\/\",\"nextItem\":{\"@type\":\"ListItem\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/2014\\\/10\\\/15\\\/extension-methods-in-cpp\\\/#listItem\",\"name\":\"Extension methods in C++\"},\"previousItem\":{\"@type\":\"ListItem\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/category\\\/it\\\/software\\\/#listItem\",\"name\":\"Software\"}},{\"@type\":\"ListItem\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/2014\\\/10\\\/15\\\/extension-methods-in-cpp\\\/#listItem\",\"position\":5,\"name\":\"Extension methods in C++\",\"previousItem\":{\"@type\":\"ListItem\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/category\\\/it\\\/software\\\/c\\\/#listItem\",\"name\":\"C++\"}}]},{\"@type\":\"Organization\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/#organization\",\"name\":\"Marius Bancila's Blog\",\"description\":\"About code. Mostly on C++\",\"url\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/\"},{\"@type\":\"Person\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/author\\\/admin\\\/#author\",\"url\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/author\\\/admin\\\/\",\"name\":\"Marius Bancila\",\"image\":{\"@type\":\"ImageObject\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/2014\\\/10\\\/15\\\/extension-methods-in-cpp\\\/#authorImage\",\"url\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/a84dd2831d955c38355ddea55df4df260809b88f36408bc14fd4eab8f7f131c9?s=96&d=mm&r=g\",\"width\":96,\"height\":96,\"caption\":\"Marius Bancila\"}},{\"@type\":\"WebPage\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/2014\\\/10\\\/15\\\/extension-methods-in-cpp\\\/#webpage\",\"url\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/2014\\\/10\\\/15\\\/extension-methods-in-cpp\\\/\",\"name\":\"Extension methods in C++\",\"description\":\"This article explores the advantages of having extension methods in C++ as proposed in the N4174 paper by Bjarne Stroustrup.\",\"inLanguage\":\"en-US\",\"isPartOf\":{\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/#website\"},\"breadcrumb\":{\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/2014\\\/10\\\/15\\\/extension-methods-in-cpp\\\/#breadcrumblist\"},\"author\":{\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/author\\\/admin\\\/#author\"},\"creator\":{\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/author\\\/admin\\\/#author\"},\"datePublished\":\"2014-10-15T16:34:34+02:00\",\"dateModified\":\"2014-10-20T15:03:32+02:00\"},{\"@type\":\"WebSite\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/#website\",\"url\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/\",\"name\":\"Marius Bancila's Blog\",\"description\":\"About code. Mostly on C++\",\"inLanguage\":\"en-US\",\"publisher\":{\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/#organization\"}}]}\n\t\t<\/script>\n\t\t<!-- All in One SEO -->\n\n","aioseo_head_json":{"title":"Extension methods in C++","description":"This article explores the advantages of having extension methods in C++ as proposed in the N4174 paper by Bjarne Stroustrup.","canonical_url":"https:\/\/mariusbancila.ro\/blog\/2014\/10\/15\/extension-methods-in-cpp\/","robots":"max-image-preview:large","keywords":"c++,standard,extension methods,n4174,stroustrup","webmasterTools":{"miscellaneous":""},"schema":{"@context":"https:\/\/schema.org","@graph":[{"@type":"Article","@id":"https:\/\/mariusbancila.ro\/blog\/2014\/10\/15\/extension-methods-in-cpp\/#article","name":"Extension methods in C++","headline":"Extension methods in C++","author":{"@id":"https:\/\/mariusbancila.ro\/blog\/author\/admin\/#author"},"publisher":{"@id":"https:\/\/mariusbancila.ro\/blog\/#organization"},"datePublished":"2014-10-15T16:34:34+02:00","dateModified":"2014-10-20T15:03:32+02:00","inLanguage":"en-US","commentCount":10,"mainEntityOfPage":{"@id":"https:\/\/mariusbancila.ro\/blog\/2014\/10\/15\/extension-methods-in-cpp\/#webpage"},"isPartOf":{"@id":"https:\/\/mariusbancila.ro\/blog\/2014\/10\/15\/extension-methods-in-cpp\/#webpage"},"articleSection":"C++, C++, extension methods, N4174, standard, Stroustrup"},{"@type":"BreadcrumbList","@id":"https:\/\/mariusbancila.ro\/blog\/2014\/10\/15\/extension-methods-in-cpp\/#breadcrumblist","itemListElement":[{"@type":"ListItem","@id":"https:\/\/mariusbancila.ro\/blog\/#listItem","position":1,"name":"Home","item":"https:\/\/mariusbancila.ro\/blog\/","nextItem":{"@type":"ListItem","@id":"https:\/\/mariusbancila.ro\/blog\/category\/it\/#listItem","name":"IT"}},{"@type":"ListItem","@id":"https:\/\/mariusbancila.ro\/blog\/category\/it\/#listItem","position":2,"name":"IT","item":"https:\/\/mariusbancila.ro\/blog\/category\/it\/","nextItem":{"@type":"ListItem","@id":"https:\/\/mariusbancila.ro\/blog\/category\/it\/software\/#listItem","name":"Software"},"previousItem":{"@type":"ListItem","@id":"https:\/\/mariusbancila.ro\/blog\/#listItem","name":"Home"}},{"@type":"ListItem","@id":"https:\/\/mariusbancila.ro\/blog\/category\/it\/software\/#listItem","position":3,"name":"Software","item":"https:\/\/mariusbancila.ro\/blog\/category\/it\/software\/","nextItem":{"@type":"ListItem","@id":"https:\/\/mariusbancila.ro\/blog\/category\/it\/software\/c\/#listItem","name":"C++"},"previousItem":{"@type":"ListItem","@id":"https:\/\/mariusbancila.ro\/blog\/category\/it\/#listItem","name":"IT"}},{"@type":"ListItem","@id":"https:\/\/mariusbancila.ro\/blog\/category\/it\/software\/c\/#listItem","position":4,"name":"C++","item":"https:\/\/mariusbancila.ro\/blog\/category\/it\/software\/c\/","nextItem":{"@type":"ListItem","@id":"https:\/\/mariusbancila.ro\/blog\/2014\/10\/15\/extension-methods-in-cpp\/#listItem","name":"Extension methods in C++"},"previousItem":{"@type":"ListItem","@id":"https:\/\/mariusbancila.ro\/blog\/category\/it\/software\/#listItem","name":"Software"}},{"@type":"ListItem","@id":"https:\/\/mariusbancila.ro\/blog\/2014\/10\/15\/extension-methods-in-cpp\/#listItem","position":5,"name":"Extension methods in C++","previousItem":{"@type":"ListItem","@id":"https:\/\/mariusbancila.ro\/blog\/category\/it\/software\/c\/#listItem","name":"C++"}}]},{"@type":"Organization","@id":"https:\/\/mariusbancila.ro\/blog\/#organization","name":"Marius Bancila's Blog","description":"About code. Mostly on C++","url":"https:\/\/mariusbancila.ro\/blog\/"},{"@type":"Person","@id":"https:\/\/mariusbancila.ro\/blog\/author\/admin\/#author","url":"https:\/\/mariusbancila.ro\/blog\/author\/admin\/","name":"Marius Bancila","image":{"@type":"ImageObject","@id":"https:\/\/mariusbancila.ro\/blog\/2014\/10\/15\/extension-methods-in-cpp\/#authorImage","url":"https:\/\/secure.gravatar.com\/avatar\/a84dd2831d955c38355ddea55df4df260809b88f36408bc14fd4eab8f7f131c9?s=96&d=mm&r=g","width":96,"height":96,"caption":"Marius Bancila"}},{"@type":"WebPage","@id":"https:\/\/mariusbancila.ro\/blog\/2014\/10\/15\/extension-methods-in-cpp\/#webpage","url":"https:\/\/mariusbancila.ro\/blog\/2014\/10\/15\/extension-methods-in-cpp\/","name":"Extension methods in C++","description":"This article explores the advantages of having extension methods in C++ as proposed in the N4174 paper by Bjarne Stroustrup.","inLanguage":"en-US","isPartOf":{"@id":"https:\/\/mariusbancila.ro\/blog\/#website"},"breadcrumb":{"@id":"https:\/\/mariusbancila.ro\/blog\/2014\/10\/15\/extension-methods-in-cpp\/#breadcrumblist"},"author":{"@id":"https:\/\/mariusbancila.ro\/blog\/author\/admin\/#author"},"creator":{"@id":"https:\/\/mariusbancila.ro\/blog\/author\/admin\/#author"},"datePublished":"2014-10-15T16:34:34+02:00","dateModified":"2014-10-20T15:03:32+02:00"},{"@type":"WebSite","@id":"https:\/\/mariusbancila.ro\/blog\/#website","url":"https:\/\/mariusbancila.ro\/blog\/","name":"Marius Bancila's Blog","description":"About code. Mostly on C++","inLanguage":"en-US","publisher":{"@id":"https:\/\/mariusbancila.ro\/blog\/#organization"}}]},"og:locale":"en_US","og:site_name":"Marius Bancila's Blog | About code. Mostly on C++","og:type":"article","og:title":"Extension methods in C++","og:description":"This article explores the advantages of having extension methods in C++ as proposed in the N4174 paper by Bjarne Stroustrup.","og:url":"https:\/\/mariusbancila.ro\/blog\/2014\/10\/15\/extension-methods-in-cpp\/","article:published_time":"2014-10-15T14:34:34+00:00","article:modified_time":"2014-10-20T13:03:32+00:00","twitter:card":"summary","twitter:title":"Extension methods in C++","twitter:description":"This article explores the advantages of having extension methods in C++ as proposed in the N4174 paper by Bjarne Stroustrup."},"aioseo_meta_data":{"post_id":"1929","title":"Extension methods in C++","description":"This article explores the advantages of having extension methods in C++ as proposed in the N4174 paper by Bjarne Stroustrup.","keywords":[{"label":"C++","value":"C++"},{"label":"standard","value":"standard"},{"label":"extension methods","value":"extension methods"},{"label":"N4174","value":"N4174"},{"label":"Stroustrup","value":"Stroustrup"}],"keyphrases":null,"primary_term":null,"canonical_url":null,"og_title":null,"og_description":null,"og_object_type":"default","og_image_type":"default","og_image_url":null,"og_image_width":null,"og_image_height":null,"og_image_custom_url":null,"og_image_custom_fields":null,"og_video":null,"og_custom_url":null,"og_article_section":null,"og_article_tags":null,"twitter_use_og":false,"twitter_card":"default","twitter_image_type":"default","twitter_image_url":null,"twitter_image_custom_url":null,"twitter_image_custom_fields":null,"twitter_title":null,"twitter_description":null,"schema":{"blockGraphs":[],"customGraphs":[],"default":{"data":{"Article":[],"Course":[],"Dataset":[],"FAQPage":[],"Movie":[],"Person":[],"Product":[],"ProductReview":[],"Car":[],"Recipe":[],"Service":[],"SoftwareApplication":[],"WebPage":[]},"graphName":"Article","isEnabled":true},"graphs":[]},"schema_type":null,"schema_type_options":null,"pillar_content":false,"robots_default":true,"robots_noindex":false,"robots_noarchive":false,"robots_nosnippet":false,"robots_nofollow":false,"robots_noimageindex":false,"robots_noodp":false,"robots_notranslate":false,"robots_max_snippet":null,"robots_max_videopreview":null,"robots_max_imagepreview":"large","priority":null,"frequency":null,"location":null,"local_seo":null,"breadcrumb_settings":null,"limit_modified_date":false,"ai":null,"created":"2021-03-18 21:10:26","updated":"2025-12-12 07:41:25","seo_analyzer_scan_date":null,"focus_keyword":null,"additional_keywords":null,"truseo_locale":null},"author_meta":{"display_name":"Marius Bancila","author_link":"https:\/\/mariusbancila.ro\/blog\/author\/admin\/"},"featured_img":null,"jetpack_publicize_connections":[],"uagb_featured_image_src":{"full":false,"thumbnail":false,"medium":false,"medium_large":false,"large":false,"1536x1536":false,"2048x2048":false},"uagb_author_info":{"display_name":"Marius Bancila","author_link":"https:\/\/mariusbancila.ro\/blog\/author\/admin\/"},"uagb_comment_info":10,"uagb_excerpt":"A few days ago Bjarne Stroustrup has published a proposal paper (N4174) to the C++ standard committee called Call syntax: x.f(y) vs. f(x,y). The following excerpt from the paper summarizes the proposal: The basic suggestion is to define x.f(y) and f(x,y) to be equivalent. In addition, to increase compatibility and modularity, I suggest we explore&hellip;","coauthors":[],"tax_additional":{"categories":{"linked":["<a href=\"https:\/\/mariusbancila.ro\/blog\/category\/it\/software\/c\/\" class=\"advgb-post-tax-term\">C++<\/a>"],"unlinked":["<span class=\"advgb-post-tax-term\">C++<\/span>"]},"tags":{"linked":["<a href=\"https:\/\/mariusbancila.ro\/blog\/category\/it\/software\/c\/\" class=\"advgb-post-tax-term\">C++<\/a>","<a href=\"https:\/\/mariusbancila.ro\/blog\/category\/it\/software\/c\/\" class=\"advgb-post-tax-term\">extension methods<\/a>","<a href=\"https:\/\/mariusbancila.ro\/blog\/category\/it\/software\/c\/\" class=\"advgb-post-tax-term\">N4174<\/a>","<a href=\"https:\/\/mariusbancila.ro\/blog\/category\/it\/software\/c\/\" class=\"advgb-post-tax-term\">standard<\/a>","<a href=\"https:\/\/mariusbancila.ro\/blog\/category\/it\/software\/c\/\" class=\"advgb-post-tax-term\">Stroustrup<\/a>"],"unlinked":["<span class=\"advgb-post-tax-term\">C++<\/span>","<span class=\"advgb-post-tax-term\">extension methods<\/span>","<span class=\"advgb-post-tax-term\">N4174<\/span>","<span class=\"advgb-post-tax-term\">standard<\/span>","<span class=\"advgb-post-tax-term\">Stroustrup<\/span>"]}},"comment_count":"10","relative_dates":{"created":"Posted 12 years ago","modified":"Updated 12 years ago"},"absolute_dates":{"created":"Posted on October 15, 2014","modified":"Updated on October 20, 2014"},"absolute_dates_time":{"created":"Posted on October 15, 2014 4:34 pm","modified":"Updated on October 20, 2014 3:03 pm"},"featured_img_caption":"","series_order":"","jetpack_shortlink":"https:\/\/wp.me\/pYNdv-v7","jetpack_sharing_enabled":true,"jetpack_likes_enabled":true,"jetpack_featured_media_url":"","_links":{"self":[{"href":"https:\/\/mariusbancila.ro\/blog\/wp-json\/wp\/v2\/posts\/1929","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/mariusbancila.ro\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/mariusbancila.ro\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/mariusbancila.ro\/blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/mariusbancila.ro\/blog\/wp-json\/wp\/v2\/comments?post=1929"}],"version-history":[{"count":13,"href":"https:\/\/mariusbancila.ro\/blog\/wp-json\/wp\/v2\/posts\/1929\/revisions"}],"predecessor-version":[{"id":1943,"href":"https:\/\/mariusbancila.ro\/blog\/wp-json\/wp\/v2\/posts\/1929\/revisions\/1943"}],"wp:attachment":[{"href":"https:\/\/mariusbancila.ro\/blog\/wp-json\/wp\/v2\/media?parent=1929"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/mariusbancila.ro\/blog\/wp-json\/wp\/v2\/categories?post=1929"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/mariusbancila.ro\/blog\/wp-json\/wp\/v2\/tags?post=1929"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}