{"id":4319,"date":"2021-07-03T08:46:53","date_gmt":"2021-07-03T06:46:53","guid":{"rendered":"https:\/\/mariusbancila.ro\/blog\/?p=4319"},"modified":"2021-07-03T08:46:56","modified_gmt":"2021-07-03T06:46:56","slug":"writing-a-simple-logging-function-in-c20","status":"publish","type":"post","link":"https:\/\/mariusbancila.ro\/blog\/2021\/07\/03\/writing-a-simple-logging-function-in-c20\/","title":{"rendered":"Writing a simple logging function in C++20"},"content":{"rendered":"\n<p class=\"wp-block-paragraph\">Logging is an important feature of any serious program. In general, one should use established libraries for logging. However, for the sake of showcasing several new features from C++20, now available in Visual Studio 2019 16.10, I will show, in this post, how one can quickly write a simple logging function.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">What I am interested in logging is the following:<\/p>\n\n\n\n<ul class=\"wp-block-list\"><li>the type of the log message, such as error, warning, or information<\/li><li>the local time when the message was logged<\/li><li>the source location with filename, function name, and source code line where the logging occurred<\/li><li>the message<\/li><\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">To get this done, I&#8217;ll use the following C++ 20 featurse:<\/p>\n\n\n\n<ul class=\"wp-block-list\"><li><a href=\"https:\/\/en.cppreference.com\/w\/cpp\/utility\/source_location\" target=\"_blank\" rel=\"noreferrer noopener\">std::source_location<\/a> class that provides information about the source code, such as file name, line number, and function name.<\/li><li><a href=\"https:\/\/en.cppreference.com\/w\/cpp\/chrono\" target=\"_blank\" rel=\"noreferrer noopener\">time zone extensions<\/a> to the chrono library<\/li><li>the <a href=\"https:\/\/en.cppreference.com\/w\/cpp\/utility\/format\" target=\"_blank\" rel=\"noreferrer noopener\">formatting library<\/a> that provides simpler functions for text formatting<\/li><\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">The end result is should be looking like the following:<\/p>\n\n\n\n<pre class=\"EnlighterJSRAW\" data-enlighter-language=\"generic\" data-enlighter-theme=\"\" data-enlighter-highlight=\"\" data-enlighter-linenumbers=\"\" data-enlighter-lineoffset=\"\" data-enlighter-title=\"\" data-enlighter-group=\"\">[I] 2021-07-03 09:07:15.5349107 GMT+3 | cpp_test.cpp:main:51 | Logging from main!\n[E] 2021-07-03 09:07:15.5477301 GMT+3 | cpp_test.cpp:execute:46 | Error in execute!<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Let&#8217;s take all these features mentioned previously one at a time. We&#8217;ll start with the type of the message. For this, I&#8217;ll simply define a scoped enum as follows:<\/p>\n\n\n\n<pre class=\"EnlighterJSRAW\" data-enlighter-language=\"cpp\" data-enlighter-theme=\"\" data-enlighter-highlight=\"\" data-enlighter-linenumbers=\"\" data-enlighter-lineoffset=\"\" data-enlighter-title=\"\" data-enlighter-group=\"\">enum class log_level : char\n{\n   Info = 'I',\n   Warning = 'W',\n   Error = 'E'\n};<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Next, is the time when the event that&#8217;s being logged occurred. The current time can be retried with <code>std::chrono::system_clock::now()<\/code>. The value returned by this call is a <code>std::chrono::system_clock::time_point<\/code>. However, this is a Coordinated Universal Time (UTC) value, and I specified that I want to display the local time. This can be done easily, with two C++20 features:<\/p>\n\n\n\n<ul class=\"wp-block-list\"><li><a href=\"https:\/\/en.cppreference.com\/w\/cpp\/chrono\/zoned_time\" target=\"_blank\" rel=\"noreferrer noopener\">std::chrono::zoned_time<\/a>, a class that represents a pairing between a time point and a time zone, enabling us to display the time within a specified time zone<\/li><li><a href=\"https:\/\/en.cppreference.com\/w\/cpp\/chrono\/current_zone\" target=\"_blank\" rel=\"noreferrer noopener\">std::chrono::current_zone()<\/a>, which is a function that returns the current time zone (from the time zone database).<\/li><\/ul>\n\n\n\n<p class=\"wp-block-paragraph\">We can use these to convert from UTC to the local time zone as follows:<\/p>\n\n\n\n<pre class=\"EnlighterJSRAW\" data-enlighter-language=\"cpp\" data-enlighter-theme=\"\" data-enlighter-highlight=\"\" data-enlighter-linenumbers=\"\" data-enlighter-lineoffset=\"\" data-enlighter-title=\"\" data-enlighter-group=\"\">auto as_local(std::chrono::system_clock::time_point const tp)\n{\n   return std::chrono::zoned_time{ std::chrono::current_zone(), tp };\n}<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">The <code>zoned_time<\/code> value can be converted to a string using the new text formatting library and the <a href=\"https:\/\/en.cppreference.com\/w\/cpp\/utility\/format\/format\" target=\"_blank\" rel=\"noreferrer noopener\">std::format()<\/a> function.<\/p>\n\n\n\n<pre class=\"EnlighterJSRAW\" data-enlighter-language=\"cpp\" data-enlighter-theme=\"\" data-enlighter-highlight=\"\" data-enlighter-linenumbers=\"\" data-enlighter-lineoffset=\"\" data-enlighter-title=\"\" data-enlighter-group=\"\">std::string to_string(auto tp)\n{\n   return std::format(\"{:%F %T %Z}\", tp);\n}<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">In this snippet, <code>%F<\/code>, <code>%T<\/code>, and <code>%Z<\/code> are specifiers that indicate how the time point will be formatted. The full list of standard specifiers for chrono is available <a href=\"https:\/\/en.cppreference.com\/w\/cpp\/chrono\/system_clock\/formatter#Format_specification\" target=\"_blank\" rel=\"noreferrer noopener\">here<\/a>. For basic and string types, the standard specifiers are available <a href=\"https:\/\/en.cppreference.com\/w\/cpp\/utility\/format\/formatter#Standard_format_specification\" target=\"_blank\" rel=\"noreferrer noopener\">here<\/a>.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">Next on the list is the source code location. The C++20 class <code>std::source_location<\/code> contains information about the file name (the <code>file_name()<\/code> function), line (the <code>line()<\/code> function), column (the <code>column()<\/code> function), and function name (the <code>function_name()<\/code> function) . The static <code>current()<\/code> function returns an object of this type initialized with information about the location of the call site.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">According to the documentation available at <a href=\"https:\/\/en.cppreference.com\/w\/cpp\/utility\/source_location\" target=\"_blank\" rel=\"noreferrer noopener\">cppreference<\/a>, the <code>file_name()<\/code> function returns the name of the file (such as <code>main.cpp<\/code>), and <code>function_name()<\/code> the full signature of the function, such as <code>int main(int, const char* const*)<\/code> or <code>S&amp; S::operator=(const S&amp;)<\/code>. However, the Visual Studio 2019 16.10 implementation, that I&#8217;m using differs, such that <code>file_name()<\/code> returns the full path of the file and <code>function_name()<\/code> only the name of the function.<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">To print the source location information, we can use the following function that returns a string formatted with <code>std::format()<\/code>. Notice that I used <code>std::filesystem::path<\/code> to extract only the file name from the path returned by <code>file_name()<\/code>.<\/p>\n\n\n\n<pre class=\"EnlighterJSRAW\" data-enlighter-language=\"cpp\" data-enlighter-theme=\"\" data-enlighter-highlight=\"\" data-enlighter-linenumbers=\"\" data-enlighter-lineoffset=\"\" data-enlighter-title=\"\" data-enlighter-group=\"\">std::string to_string(std::source_location const source)\n{\n   return std::format(\"{}:{}:{}\", \n      std::filesystem::path(source.file_name()).filename().string(),\n      source.function_name(),\n      source.line());\n}<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Last but not least, is the logging function that looks as follows:<\/p>\n\n\n\n<pre class=\"EnlighterJSRAW\" data-enlighter-language=\"cpp\" data-enlighter-theme=\"\" data-enlighter-highlight=\"\" data-enlighter-linenumbers=\"\" data-enlighter-lineoffset=\"\" data-enlighter-title=\"\" data-enlighter-group=\"\">void log(log_level const level, \n         std::string_view const message, \n         std::source_location const source = std::source_location::current())\n{\n   std::cout\n      &lt;&lt; std::format(\"[{}] {} | {} | {}\", \n                     static_cast&lt;char>(level), \n                     to_string(as_local(std::chrono::system_clock::now())), \n                     to_string(source), \n                     message)\n      &lt;&lt; '\\n';\n}<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">This function takes three arguments: the log level, the message to be logged, and a source location object constructed with a call to <code>std::source_location::current()<\/code> (which is a <code>consteval<\/code> function, meaning it&#8217;s an immediate function that produces a compile-time constant value).<\/p>\n\n\n\n<p class=\"wp-block-paragraph\">With all these in place, we can call the log() function from our code as follows:<\/p>\n\n\n\n<pre class=\"EnlighterJSRAW\" data-enlighter-language=\"cpp\" data-enlighter-theme=\"\" data-enlighter-highlight=\"\" data-enlighter-linenumbers=\"\" data-enlighter-lineoffset=\"\" data-enlighter-title=\"\" data-enlighter-group=\"\">void execute(int, double)\n{\n   log(log_level::Error, \"Error in execute!\");\n}\n\nint main()\n{\n   log(log_level::Info, \"Logging from main!\");\n   execute(0, 0);\n}<\/pre>\n\n\n\n<p class=\"wp-block-paragraph\">Of course, these new features showcased here (especially the text formatting and the calendar and time zone extensions) are more complex, provide more features, and require more study. However, this small example should be a good example how these new features can be used together to help us simplify our code.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Logging is an important feature of any serious program. In general, one should use established libraries for logging. However, for the sake of showcasing several new features from C++20, now available in Visual Studio 2019 16.10, I will show, in this post, how one can quickly write a simple logging function.<\/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,543,488,637],"class_list":["post-4319","post","type-post","status-publish","format-standard","hentry","category-c","tag-c","tag-c20","tag-chrono","tag-text-formatting"],"aioseo_notices":[],"aioseo_head":"\n\t\t<!-- All in One SEO 5.0.3 - aioseo.com -->\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++,c++20,chrono,text formatting\" \/>\n\t<link rel=\"canonical\" href=\"https:\/\/mariusbancila.ro\/blog\/2021\/07\/03\/writing-a-simple-logging-function-in-c20\/\" \/>\n\t\t<meta name=\"generator\" content=\"All in One SEO (AIOSEO) 5.0.3\" \/>\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=\"Writing a simple logging function in C++20\" \/>\n\t\t<meta property=\"og:url\" content=\"https:\/\/mariusbancila.ro\/blog\/2021\/07\/03\/writing-a-simple-logging-function-in-c20\/\" \/>\n\t\t<meta property=\"article:published_time\" content=\"2021-07-03T06:46:53+00:00\" \/>\n\t\t<meta property=\"article:modified_time\" content=\"2021-07-03T06:46:56+00:00\" \/>\n\t\t<meta name=\"twitter:card\" content=\"summary\" \/>\n\t\t<meta name=\"twitter:title\" content=\"Writing a simple logging function in C++20\" \/>\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\\\/2021\\\/07\\\/03\\\/writing-a-simple-logging-function-in-c20\\\/#article\",\"name\":\"Writing a simple logging function in C++20\",\"headline\":\"Writing a simple logging function in C++20\",\"author\":{\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/author\\\/admin\\\/#author\"},\"publisher\":{\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/#organization\"},\"datePublished\":\"2021-07-03T08:46:53+02:00\",\"dateModified\":\"2021-07-03T08:46:56+02:00\",\"inLanguage\":\"en-US\",\"commentCount\":3,\"mainEntityOfPage\":{\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/2021\\\/07\\\/03\\\/writing-a-simple-logging-function-in-c20\\\/#webpage\"},\"isPartOf\":{\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/2021\\\/07\\\/03\\\/writing-a-simple-logging-function-in-c20\\\/#webpage\"},\"articleSection\":\"C++, C++, c++20, chrono, text formatting\"},{\"@type\":\"BreadcrumbList\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/2021\\\/07\\\/03\\\/writing-a-simple-logging-function-in-c20\\\/#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\\\/2021\\\/07\\\/03\\\/writing-a-simple-logging-function-in-c20\\\/#listItem\",\"name\":\"Writing a simple logging function in C++20\"},\"previousItem\":{\"@type\":\"ListItem\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/category\\\/it\\\/software\\\/#listItem\",\"name\":\"Software\"}},{\"@type\":\"ListItem\",\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/2021\\\/07\\\/03\\\/writing-a-simple-logging-function-in-c20\\\/#listItem\",\"position\":5,\"name\":\"Writing a simple logging function in C++20\",\"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\\\/2021\\\/07\\\/03\\\/writing-a-simple-logging-function-in-c20\\\/#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\\\/2021\\\/07\\\/03\\\/writing-a-simple-logging-function-in-c20\\\/#webpage\",\"url\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/2021\\\/07\\\/03\\\/writing-a-simple-logging-function-in-c20\\\/\",\"name\":\"Writing a simple logging function in C++20\",\"inLanguage\":\"en-US\",\"isPartOf\":{\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/#website\"},\"breadcrumb\":{\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/2021\\\/07\\\/03\\\/writing-a-simple-logging-function-in-c20\\\/#breadcrumblist\"},\"author\":{\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/author\\\/admin\\\/#author\"},\"creator\":{\"@id\":\"https:\\\/\\\/mariusbancila.ro\\\/blog\\\/author\\\/admin\\\/#author\"},\"datePublished\":\"2021-07-03T08:46:53+02:00\",\"dateModified\":\"2021-07-03T08:46:56+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":"Writing a simple logging function in C++20","description":"","canonical_url":"https:\/\/mariusbancila.ro\/blog\/2021\/07\/03\/writing-a-simple-logging-function-in-c20\/","robots":"max-image-preview:large","keywords":"c++,c++20,chrono,text formatting","webmasterTools":{"miscellaneous":""},"schema":{"@context":"https:\/\/schema.org","@graph":[{"@type":"Article","@id":"https:\/\/mariusbancila.ro\/blog\/2021\/07\/03\/writing-a-simple-logging-function-in-c20\/#article","name":"Writing a simple logging function in C++20","headline":"Writing a simple logging function in C++20","author":{"@id":"https:\/\/mariusbancila.ro\/blog\/author\/admin\/#author"},"publisher":{"@id":"https:\/\/mariusbancila.ro\/blog\/#organization"},"datePublished":"2021-07-03T08:46:53+02:00","dateModified":"2021-07-03T08:46:56+02:00","inLanguage":"en-US","commentCount":3,"mainEntityOfPage":{"@id":"https:\/\/mariusbancila.ro\/blog\/2021\/07\/03\/writing-a-simple-logging-function-in-c20\/#webpage"},"isPartOf":{"@id":"https:\/\/mariusbancila.ro\/blog\/2021\/07\/03\/writing-a-simple-logging-function-in-c20\/#webpage"},"articleSection":"C++, C++, c++20, chrono, text formatting"},{"@type":"BreadcrumbList","@id":"https:\/\/mariusbancila.ro\/blog\/2021\/07\/03\/writing-a-simple-logging-function-in-c20\/#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\/2021\/07\/03\/writing-a-simple-logging-function-in-c20\/#listItem","name":"Writing a simple logging function in C++20"},"previousItem":{"@type":"ListItem","@id":"https:\/\/mariusbancila.ro\/blog\/category\/it\/software\/#listItem","name":"Software"}},{"@type":"ListItem","@id":"https:\/\/mariusbancila.ro\/blog\/2021\/07\/03\/writing-a-simple-logging-function-in-c20\/#listItem","position":5,"name":"Writing a simple logging function in C++20","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\/2021\/07\/03\/writing-a-simple-logging-function-in-c20\/#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\/2021\/07\/03\/writing-a-simple-logging-function-in-c20\/#webpage","url":"https:\/\/mariusbancila.ro\/blog\/2021\/07\/03\/writing-a-simple-logging-function-in-c20\/","name":"Writing a simple logging function in C++20","inLanguage":"en-US","isPartOf":{"@id":"https:\/\/mariusbancila.ro\/blog\/#website"},"breadcrumb":{"@id":"https:\/\/mariusbancila.ro\/blog\/2021\/07\/03\/writing-a-simple-logging-function-in-c20\/#breadcrumblist"},"author":{"@id":"https:\/\/mariusbancila.ro\/blog\/author\/admin\/#author"},"creator":{"@id":"https:\/\/mariusbancila.ro\/blog\/author\/admin\/#author"},"datePublished":"2021-07-03T08:46:53+02:00","dateModified":"2021-07-03T08:46:56+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":"Writing a simple logging function in C++20","og:url":"https:\/\/mariusbancila.ro\/blog\/2021\/07\/03\/writing-a-simple-logging-function-in-c20\/","article:published_time":"2021-07-03T06:46:53+00:00","article:modified_time":"2021-07-03T06:46:56+00:00","twitter:card":"summary","twitter:title":"Writing a simple logging function in C++20"},"aioseo_meta_data":{"post_id":"4319","title":null,"description":null,"keywords":[],"keyphrases":{"focus":[],"additional":[]},"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":"","og_custom_url":null,"og_article_section":null,"og_article_tags":[],"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":{"id":"aioseo-article-636966901a8dd","slug":"article","graphName":"Article","label":"Article","properties":{"type":"BlogPosting","name":"#post_title","headline":"#post_title","description":"#post_excerpt","image":"","keywords":"","author":{"name":"#author_name","url":"#author_url"},"dates":{"include":true,"datePublished":"","dateModified":""}}},"Course":[],"Dataset":[],"FAQPage":[],"Movie":[],"Person":[],"Product":[],"ProductReview":[],"Car":[],"Recipe":[],"Service":[],"SoftwareApplication":[],"WebPage":[]},"graphName":"Article","isEnabled":true},"graphs":[]},"schema_type":"default","schema_type_options":"{\"article\":{\"articleType\":\"BlogPosting\"},\"course\":{\"name\":\"\",\"description\":\"\",\"provider\":\"\"},\"faq\":{\"pages\":[]},\"product\":{\"reviews\":[]},\"recipe\":{\"ingredients\":[],\"instructions\":[],\"keywords\":[]},\"software\":{\"reviews\":[],\"operatingSystems\":[]},\"webPage\":{\"webPageType\":\"WebPage\"}}","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":"-1","robots_max_videopreview":"-1","robots_max_imagepreview":"large","priority":null,"frequency":"default","location":null,"local_seo":{"locations":{"business":{"name":"","businessType":"","image":"","areaServed":"","urls":{"website":"","aboutPage":"","contactPage":""},"address":{"streetLine1":"","streetLine2":"","zipCode":"","city":"","state":"","country":"","addressFormat":"#streetLineOne\n#streetLineTwo\n#city, #state #zipCode"},"contact":{"email":"","phone":"","phoneFormatted":"","fax":"","faxFormatted":""},"ids":{"vat":"","tax":"","chamberOfCommerce":""},"payment":{"priceRange":"","currenciesAccepted":"","methods":""}}},"openingHours":{"useDefaults":true,"show":true,"alwaysOpen":false,"use24hFormat":false,"timezone":"","labels":{"closed":"","alwaysOpen":""},"days":{"monday":{"open24h":false,"closed":false,"openTime":"09:00","closeTime":"17:00"},"tuesday":{"open24h":false,"closed":false,"openTime":"09:00","closeTime":"17:00"},"wednesday":{"open24h":false,"closed":false,"openTime":"09:00","closeTime":"17:00"},"thursday":{"open24h":false,"closed":false,"openTime":"09:00","closeTime":"17:00"},"friday":{"open24h":false,"closed":false,"openTime":"09:00","closeTime":"17:00"},"saturday":{"open24h":false,"closed":false,"openTime":"09:00","closeTime":"17:00"},"sunday":{"open24h":false,"closed":false,"openTime":"09:00","closeTime":"17:00"}}}},"breadcrumb_settings":null,"limit_modified_date":false,"ai":null,"created":"2021-07-03 05:51:19","updated":"2025-12-12 07:56: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":3,"uagb_excerpt":"Logging is an important feature of any serious program. In general, one should use established libraries for logging. However, for the sake of showcasing several new features from C++20, now available in Visual Studio 2019 16.10, I will show, in this post, how one can quickly write a simple logging function.","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\">c++20<\/a>","<a href=\"https:\/\/mariusbancila.ro\/blog\/category\/it\/software\/c\/\" class=\"advgb-post-tax-term\">chrono<\/a>","<a href=\"https:\/\/mariusbancila.ro\/blog\/category\/it\/software\/c\/\" class=\"advgb-post-tax-term\">text formatting<\/a>"],"unlinked":["<span class=\"advgb-post-tax-term\">C++<\/span>","<span class=\"advgb-post-tax-term\">c++20<\/span>","<span class=\"advgb-post-tax-term\">chrono<\/span>","<span class=\"advgb-post-tax-term\">text formatting<\/span>"]}},"comment_count":"3","relative_dates":{"created":"Posted 5 years ago","modified":"Updated 5 years ago"},"absolute_dates":{"created":"Posted on July 3, 2021","modified":"Updated on July 3, 2021"},"absolute_dates_time":{"created":"Posted on July 3, 2021 8:46 am","modified":"Updated on July 3, 2021 8:46 am"},"featured_img_caption":"","series_order":"","jetpack_shortlink":"https:\/\/wp.me\/pYNdv-17F","jetpack_sharing_enabled":true,"jetpack_likes_enabled":true,"jetpack_featured_media_url":"","_links":{"self":[{"href":"https:\/\/mariusbancila.ro\/blog\/wp-json\/wp\/v2\/posts\/4319","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=4319"}],"version-history":[{"count":2,"href":"https:\/\/mariusbancila.ro\/blog\/wp-json\/wp\/v2\/posts\/4319\/revisions"}],"predecessor-version":[{"id":4321,"href":"https:\/\/mariusbancila.ro\/blog\/wp-json\/wp\/v2\/posts\/4319\/revisions\/4321"}],"wp:attachment":[{"href":"https:\/\/mariusbancila.ro\/blog\/wp-json\/wp\/v2\/media?parent=4319"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/mariusbancila.ro\/blog\/wp-json\/wp\/v2\/categories?post=4319"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/mariusbancila.ro\/blog\/wp-json\/wp\/v2\/tags?post=4319"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}