Advertisement
Поиск  
Always will be ready notify the world about expectations as easy as possible: job change page
Jul 7, 2021

Formatting Strings using Templates in C#

Автор:
Changhui Xu
Источник:
Просмотров:
907

C# has a feature, String Interpolation, to format strings in a flexible and readable way. The following example demonstrates the way how we usually output a string when we have data beforehand then pass data to the template string.

var name = "April";
var dob = new DateTime(2000, 4, 10);
Console.WriteLine($"Her name is {name} and her birthday is on {dob:MM/dd/yyyy}, which is in {dob:MMMM}.");
// Console Output:
// Her name is April and sher birthday is on 04/10/2000, which is in April.

On the other hand, the String Interpolation doesn’t work in some scenarios when we want to format certain strings following predefined templates. The string can be, for example, a log message, an alert, an Email template, and so on.

To solve this problem, we can use some NuGet packages (e.g., Nustache, Stubble, mustache#) to render templates by substituting parameters that are wrapped in specific syntaxes with desired values. These libraries work like view engines that are able to compile templates with complex logic.

In this article, instead of using those libraries, I will show you two simple ways to substitute parameters with values in a string template. The full solution can be found in my GitHub repository.

string.Format()

The most common way to format strings is using the string.Format() method. This method takes a template which contains indexes as placeholders and takes a list of objects for stubbing out indexed parameters. Let's take a look at the following example.

const string template = "Her name is {0} and her birthday is on {1:MM/dd/yyyy}, which is in {1:MMMM}.";
var s = string.Format(template, "April", new DateTime(2000, 4, 10);
Console.WriteLine(s);
// Console Output:
// Her name is April and her birthday is on 04/10/2000, which is in April.
Console.WriteLine(template, "April", new DateTime(2000, 4, 10));
// Console Output:
// Her name is April and her birthday is on 04/10/2000, which is in April.

In the code above, line 1 defines the string template, which is a constant and contains two indexes: 0 and 1. Besides the indexes, we can also add the formatter to each object. Line 2 generates a string based on two objects, and line 3 writes the string to the Console. Similarly, line 4 writes a string directly to Console.

Using the string.Format() method, we can easily replace the placeholders with desired values. The only problem is that indexes do not convey much meaning when we read the code. Therefore, this way works the best when the number of parameters is small.

Template Modeling

In case when a string template contains many parameters, we probably want to use named parameters instead of indexes to improve the readability. Then we need to utilize some kind of template syntax like mustache or handlebar. Rather than installing a third-party library, we can quickly implement something on our own. I name this way as “template modeling” because we are going to model the target string as a class.

Let’s take a look at the following example.

var s = new MyString("April", new DateTime(2000, 4, 10));
Console.WriteLine(s);

public class MyString
{
    private const string Template = @"Her name is {name} and her birthday is on {dob}, which is in {month}.";
    private readonly Dictionary<string, string> _parameters = new();
    
    public MyString(string name, DateTime dob)
    {
        // validate parameters before assignment
        
        _parameters.Add(@"{name}", name);
        _parameters.Add(@"{dob}", $"{dob:MM/dd/yyyy}");
        _parameters.Add(@"{month}", $"{dob:MMMM}");
    }
    
    public override string ToString()
    {
        return _parameters.Aggregate(Template, (s, kv) => s.Replace(kv.Key, kv.Value));
    }
}

In the code snippet above, we define a class MyString to model the construction and rendering of a predefined string template. In the MyString class, a private dictionary _parameters is used to store the string placeholders and their values. The named placeholders can be wrapped with some escape characters that are distinct from the other content in the template.

The constructor, lines 9 to 16, can be served as a validator for parameters so that they are ensured to be correct or have some fallback values, and can be served as value transformer so that each template segment can be replaced with a transformed value based on business logic.

Lastly, the public ToString() method simply returns the formatted the string based on the static template and input parameters. Inside the ToString() method, line 20 uses a LINQ expression which gracefully replaces all template segments with stored values.

This way allows us to easily write unit tests with different parameters.

A word of caution is that you may want to sanitize the objects so that they won’t mess up with your template. For example, it is a good idea to sanitize the inputs for an HTML email template to avoid injection. Also, don’t use any of these methods to generate SQL queries or statements. Entity Framework has already have a method for generating raw SQL

Похожее
May 31, 2023
Author: Yohan Malshika
Understanding uow to use And and Or operators with Expression TreesAs a C# developer, you may have come across scenarios where you need to build complex logical expressions dynamically based on user input or other dynamic factors. In such cases,...
Jun 29, 2023
Author: Megha Prasad
Attributes and decorators, which allow you to attach metadata to classes, properties, and methods.AttributesAttributes in C# allow you to attach metadata to your classes, methods, and other code elements. This metadata can then be used at runtime to modify the...
Jul 23, 2023
Unlocking Resilience and Transient-fault-handling in your C# CodeIn an ideal world, every operation we execute, every API we call, and every database we query, would always work flawlessly. Unfortunately, we live in a world where network outages, server overloads, and...
месяц назад
Рассмотрим интересную задачу по разработке игры «Крестики Нолики» на языке C#. Наш проект будет запускаться в консоли и потребует креативное мышление для решения задачи. Ваша задача — реализовать консольную игру "крестики-нолики" с использованием языка программирования C#. Вам нужно создать игровое поле,...
Написать сообщение
Почта
Имя
*Сообщение


© 1999–2024 WebDynamics
1980–... Sergey Drozdov
Area of interests: .NET Framework | .NET Core | C# | ASP.NET | Windows Forms | WPF | HTML5 | CSS3 | jQuery | AJAX | Angular | React | MS SQL Server | Transact-SQL | ADO.NET | Entity Framework | IIS | OOP | OOA | OOD | WCF | WPF | MSMQ | MVC | MVP | MVVM | Design Patterns | Enterprise Architecture | Scrum | Kanban