برچسب: Care

  • How to use String.Format – and why you should care about it | Code4IT


    Is string.Format obsolete? Not at all, it still has cards to play! Let’s see how we can customize format and create custom formatters.

    Table of Contents

    Just a second! 🫷
    If you are here, it means that you are a software developer.
    So, you know that storage, networking, and domain management have a cost .

    If you want to support this blog, please ensure that you have disabled the adblocker for this site.
    I configured Google AdSense to show as few ADS as possible – I don’t want to bother you with lots of ads, but I still need to add some to pay for the resources for my site.

    Thank you for your understanding.
    Davide

    Formatting strings is one of the basic operations we do in our day-by-day job. Many times we create methods to provide specific formatting for our data, but not always we want to implement additional methods for every type of formatting we need – too many similar methods will clutter our code.

    Let’s say that you have this simple class:

    class CapturedPokemon{
      public string Name { get; set; }
      public int PokedexIndex { get; set; }
      public decimal Weight { get; set; }
      public decimal Height { get; set; }
      public DateTime CaptureDate { get; set; }
    }
    

    and an instance of that class:

    var pkm = new CapturedPokemon
    {
        Name = "Garchomp",
        PokedexIndex = 445,
        Height = 1.9m,
        Weight = 95.0m,
        CaptureDate = new DateTime(2020, 5, 6, 14, 55, 23)
    };
    

    How can we format the pkm variable to provide useful information on our UI?

    The most simple ways are using concatenation, formatting, or string interpolation.

    Differences between concatenation, formatting, and interpolation

    Concatenation is the simplest way: you concatenate strings with the + operator.

    var messageWithConcatenation= "I caught a " + pkm.Name + " on " + pkm.CaptureDate.ToString("yyyy-MM-dd");
    

    There are 2 main downsides:

    1. it’s hard to read and maintains, with all those open and closed quotes
    2. it’s highly inefficient, since strings are immutable and, every time you concatenate a string, it creates a whole new string.

    Interpolation is the ability to wrap a variable inside a string and, eventually, call methods on it while creating the string itself.

    var messageWithInterpolation = $"I caught a {pkm.Name} on {pkm.CaptureDate.ToString("yyyy-MM-dd")}";
    

    As you see, it’s easier to read than simple concatenation.

    The downside of this approach is that here you don’t have a visual understanding of what is the expected string, because the variables drive your attention away from the message you are building with this string.

    PS: notice the $ at the beginning of the string and the { and } used to interpolate the values.

    Formatting is the way to define a string using positional placeholders.

    var messageWithFormatting = String.Format("I caught a {0} on {1}", pkm.Name, pkm.CaptureDate.ToString("yyyy-MM-dd"));
    

    We are using the Format static method from the String class to define a message, set up the position of the elements and the elements themselves.

    Now we have a visual clue of the general structure of the string, but we don’t have a hint of which values we can expect.

    Even if string.Format is considered obsolete, there is still a reason to consider it when formatting strings: this class can help you format the values with default and custom formatters.

    But first, a quick note on the positioning.

    Positioning and possible errors in String.Format

    As you may expect, for string.Format positioning is 0-based. But if it’s true that the numbers must start with zero, it’s also true that the actual position doesn’t count. In fact, the next two strings are the same:

    var m1 = String.Format("I caught a {0} on {1}", pkm.Name, pkm.CaptureDate);
    var m2 = String.Format("I caught a {1} on {0}", pkm.CaptureDate, pkm.Name);
    

    Of course, if you swap the positioning in the string, you must also swap the order of the parameters.

    Since we are only specifying the position, we can use the same value multiple times inside the same string, just by repeating the placeholder:

    String.Format("I caught a {0} (YES, {0}!) on {1}", pkm.Name, pkm.CaptureDate);
    // I caught a Garchomp (YES, Garchomp!) on 06/05/2020 14:55:23
    

    What happens if the number of position is different from the number of arguments?

    If there are more parameters than placeholders, the exceeding ones are simply ignored:

    String.Format("I caught a {0} on {1}", pkm.Name, pkm.CaptureDate, pkm.PokedexIndex);
    /// I caught a Garchomp on 06/05/2020 14:55:23
    

    On the contrary, if there are more placeholders than parameters, we will get a FormatException:

    String.Format("I caught a {0} on {1}", pkm.Name);
    

    with the message

    Index (zero based) must be greater than or equal to zero and less than the size of the argument list_.

    How to format numbers

    You can print numbers with lots of different formats, you know. Probably you’ve already done it with the ToString method. Well, here’s almost the same.

    You can use all the standard numeric formats as formatting parameters.

    For example, you can write a decimal as a currency value by using C or c:

    String.Format("{0:C}", 12.7885m);
    // £12.79
    

    In this way, you can use the symbols belonging to the current culture (in this case, we can see the £) and round the value to the second decimal.

    If you want to change the current culture, you must setup it in a global way or, at least, change the culture for the current thread:

    Thread.CurrentThread.CurrentCulture = new System.Globalization.CultureInfo("it-IT");
    
    Console.WriteLine(String.Format("{0:C}", 12.7885m)); // 12,79 €
    

    If you want to handle numbers with different formats, you can all the formats defined in the official documentation (linked above). Among them we can find, for example, the fixed-point formatter that can manage both the sign and the number of decimal digits:

    String.Format("{0:f8}", 12.7885m) //12.78850000
    

    With :f8 here we are saying that we want the fixed-point format with 8 decimal digits.

    How to format dates

    As per numbers, the default representation of dates is the one provided by the ToString method.

    String.Format("{0}", new System.DateTime(2020,5,8,1,6,0))
    // 08/05/2020 01:06:00
    

    This is useful, but not very customizable.
    Luckily we can use our usual formatting strings to print the date as we want.

    For example, if you want to print only the date, you can use :d in the formatting section:

    String.Format("{0:d}", new System.DateTime(2020,5,8,1,6,0))
    // 08/05/2020
    

    and you can use :t if you are interested only in the time info:

    String.Format("{0:t}", new System.DateTime(2020,5,8,1,6,0))
    // 01:06
    

    Of course, you can define your custom formatting to get the info in the format you want:

    String.Format("{0:yyyy-MM-dd hh:mm}", new System.DateTime(2020,5,8,1,6,0))
    // 2020-05-08 01:06
    

    PSS! Remember how the current culture impacts the result!

    How to define custom formats

    As you may imagine, the default value used for formatting is the one defined by ToString. We can prove it by simply defining the ToString method in our CapturedPokemon class

    class CapturedPokemon
    {
      // fields...
    
      public override string ToString()
      {
        return $"Name: {Name} (#{PokedexIndex})";
      }
    }
    

    and by passing the whole pkm variable defined at the beginning of this article:

    String.Format("{0}", pkm)
    // Name: Garchomp (#445)
    

    But, of course, you may want to use different formatting across your project.

    Let’s define a formatter for my CapturedPokemon class. This class must implement both IFormatProvider and ICustomFormatter interfaces.

    public class PokemonFormatter : IFormatProvider, ICustomFormatter
    {
      // todo
    }
    

    First of all, let’s implement the GetFormat method from IFormatProvider with the default code that works for every custom formatter we are going to build:

    public object GetFormat(Type formatType)
    {
      if (formatType == typeof(ICustomFormatter))
        return this;
      else
        return null;
    }
    

    And then we can define the core of our formatter in the Format method. It accepts 3 parameters: format is the string that we pass after the : symbol, like in :d3; arg is a generic object that references the object to be formatted and formatProvider is… well, I don’t know! Drop me a comment if you know how to use it and why!

    Moving on, and skipping the initial checks, we can write the core of the formatting like this:

    switch (format.ToUpper())
    {
      case "FULL": return $"{pokemon.Name} (#{pokemon.PokedexIndex}) caught on {pokemon.CaptureDate}";
      case "POKEDEX": return $"{pokemon.Name} (#{pokemon.PokedexIndex})";
      case "NAME": return $"{shortName}";
      default:
        throw new FormatException($"The format {format} is not valid");
    }
    

    So the point is to define different formats, pass one of them in the format parameter, and apply it to the arg object.

    We can then use the String.Format method in this way:

    String.Format(new PokemonFormatter(), "{0:full}", pkm) // Garchomp (#445) caught on 06/05/2020 14:55:23
    String.Format(new PokemonFormatter(), "{0:pokedex}", pkm) // Garchomp (#445)
    String.Format(new PokemonFormatter(), "{0:name}", pkm) //Grchmp
    

    If you are interested in the whole code, have find it at the end of the article.

    By the way, why should we care about formatters? Because we must always take into account the separation of concerns. Why would the CapturedPokemon class expose a method for each formatting value? It should be in the scope of the class definition itself, so it’s better to write it somewhere else and use it only when it’s needed.

    Conclusion

    Using String.Format is now considered a vintage way to format strings. Even Microsoft itself recommends to use string interpolation because it is more readable (syntax highlighting helps you see better what are the values) and more flexible (because you directly create the string instead of calling an additional method – string.Format itself).

    By the way, I think it’s important to get to know even String.Format because it can be useful not only for readability (because you can see the structure of the returned string even without looking at the actual parameters used) but also because you can create strings dynamically, like in this example:

    string en = "My name is {0}";
    string it = "Il mio nome è {0}";
    
    var actualString = DateTime.UtcNow.Ticks % 2 == 0 ? it : en;
    
    Console.WriteLine(string.Format(actualString, "Davide"));
    

    If you want to read more about string.Format, just head to the Microsoft documentation, where you can find lots of examples.

    In the end, here’s the full code of the Format method for our PokemonFormatter class.

    public string Format(string format, object arg, IFormatProvider formatProvider)
    {
      if (!this.Equals(formatProvider)) { return null; }
    
      if (!(arg is CapturedPokemon pokemon)) { return null; }
    
      if (string.IsNullOrWhiteSpace(format))
        format = "full";
    
      var shortName = Regex.Replace(pokemon.Name, "a|e|i|o|u", "");
    
      switch (format.ToUpper())
      {
        case "FULL": return $"{pokemon.Name} (#{pokemon.PokedexIndex}) caught on {pokemon.CaptureDate}";
        case "POKEDEX": return $"{pokemon.Name} (#{pokemon.PokedexIndex})";
        case "NAME": return $"{shortName}";
        default:
          throw new FormatException($"The format {format} is not valid");
      }
    }
    

    Happy coding!



    Source link

  • Craft, Clarity, and Care: The Story and Work of Mengchu Yao

    Craft, Clarity, and Care: The Story and Work of Mengchu Yao


    Hi, I’m Mengchu Yao from Taiwan, and I am currently based in Tokyo, Japan, where I work as a web designer at baqemono.inc.

    I’m truly grateful to be able to pursue my design career in a cross-cultural environment. The life here allows me to appreciate small things and encourages me to stay curious and open minded.

    Featured Work

    Movie × AI model

    We created the website for AI model Inc., a company that leverages AI models and virtual personalities to offer digital transformation (DX) services. The site was created to showcase their AI video generation solutions.

    Personal notes

    This website design is centered around the concept of “natural and elegant AI-generated visuals”. One of the key challenges was to present a large number of dynamic, immersive visual elements and interactions within a single-page layout. We spent a lot of time finding the right balance between animation and delivering messages, ensuring that every motion looks beautiful and meaningful at the same time

    This was also time that I sketched the animation for almost every section myself, working closely with developers to fine-tune the motion expressions. The process was both challenging and fascinating, which is why it was rewarding and significant for my growth.

    Vlag yokohama

    We created the official website for “Vlag yokohama,” a new members-only creative lounge and workspace located on the top (42nd) floor of the THE YOKOHAMA FRONT at Yokohama Station.

    Personal notes

    This project was a rare opportunity that allowed me to explore and be creative while using the brand guidelines as a foundation, in response to the request “to use the Yokohama cityscape as the backbone of visuals while incorporating elements that evoke the feeling of wind and motion.”

    One thoughtful touch was the main visual on the homepage. It automatically changes during the time of day: morning, afternoon, and evening, which represents Yokohama’s ambiances and gives a subtle delight to the browsing experience.

    ANGELUX

    We created a brand-new corporate website for Angelux Co., Ltd., a company founded in 1987 that specializes in beauty salons and spas operations, with product development and sales in cosmetics.

    Personal notes

    This project began with the client’s request to clearly distinguish between the service website and the corporate site, and to position the latter as a recruitment platform that authentically reflects the people behind the brand.

    To embody Angelux’s strong emphasis on craftsmanship, we featured actual treatment scenes in the main visual. The overall design blends a sense of classic professionalism with a soft modern aesthetic, creating a calm and reassuring atmosphere. This approach not only helps build trust in the company but also effectively appeals to potential talent interested in joining Angelux.

    The visual design incorporated elements reminiscent of high-quality cosmetics that conveys the clean beauty and clarity of skincare.

    infordio

    We redesigned the official website for Infodio Inc., a company that specializes in advanced technologies such as AI-OCR and Natural Language Processing (NLP), and offers high-speed, automated transcription products and services.

    Personal notes

    The original website failed to effectively communicate “AI as core”, and often mislead the client’s applicants. To resolve the issue, our strategy was to emphesize the products. The revamp successfully gives the true essence of the brand and attracts the right potential talents with clear messaging.

    For the visuals, we started from scratch. It was challenging but also the most fun part. As the products were the focal point of the design, the key was to show both the authenticity and visual appeal.

    Background

    After getting my master’s degree in Information Design, I joined the Tokyo-based digital design studio, baqemono.inc., I have had the opportunity to lead several challenging and creatively fulfilling projects from the early stages of my career.

    These experiences have shaped me tremendously and deepened my passion for this field. Throughout this journey, the studio’s founder has remained the designer I admire the most — a constant source of inspiration whose presence reminds me to approach every project with both respect and enthusiasm.

    Design Philosophy

    A strong concept is your north star

    I believe every design should be built upon a clear and compelling core idea. Whenever I begin a project, I always ask myself: “What am I designing for?”

    Structure comes first

    Before diving into visuals, I make sure I spend enough time on wireframes and the overall structure.
If the content and hierarchy aren’t clearly defined at the start, the rest of the bits and pieces become noises that cloud judgment. A solid framework helps me stay focused and gives me room to refine the details.

    Listen to the discomfort in your gut

    Whenever I feel that something’s “not quite right”, I always know I’d have to come back to take another look because these subtle feelings often point to something important.
 I believe that as designers we should be honest with ourselves, take a pause to examine, and revise. Each small tweak is a step closer to your truth.

    You have to genuinely love it

    I also believe that every designer should love his/her own work so the work will bring its impact.
This isn’t just about aesthetics — it’s about fully owning the concept, the details, and the final outcome.

    Teamwork is everything

    No project is ever completed by me alone — it’s always the result of a team effort.
 I deeply respect every member involved, and I constantly ask myself: “What can I do to make the collaboration smoother for everyone?”

    Tools and Techniques

    • Photoshop
    • Figma
    • After Effects
    • Eagle

    Future goals

    My main goal for the year is to start building my portfolio website. I’ve been mainly sharing my work on social media, but as I’ve gained more hands-on experience and creative outputs over time, I realized that it’s important to have a dedicated space that fully reflects who I am as a designer today.

    Recently, I started to make some changes in my daily routine, such as better sleeping hours and becoming a morning person to be more focused and productive for my work. My mind is clearer, and my body feels great, just as if I’m preparing myself for the next chapter of my creative journey.

    Final Thoughts

    Giving someone advice is always a little tricky for me, but one phrase that has resonated deeply with me throughout my journey is: “Go slow to go fast”. Finding your own balance between creating and resting while continuing to stay passionate about life is, to me, the most important thing of all.

    Thank you so much for taking the time to read this. I hope you enjoyed the works and thoughts I’ve shared!

    A heartfelt thanks as well to Codrops and Manoela for inviting me to be part of this Designer Spotlight. Ever since I stepped into the world of web design, Codrops has been a constant source of inspiration, showing me so many amazing works and creators. I’m truly honored and grateful to be featured among them.

    Contact

    I’m always excited to connect with people to share ideas and explore new opportunities together.
If anything here speaks to you, feel free to reach out — I’d love to chat more and hear your thoughts!
    I also share updates on my latest projects from time to time on social media, so feel free to drop by and say hi 😊



    Source link