Skip to content
Lesson 4 of 15

Step 1 of 5 · Reading · ~4 min

Learn

Strings and Interfaces

Strings

Text in TypeScript is the string primitive: an immutable sequence of characters with a rich set of methods. By the end of this lesson you can take a string apart, change the pieces, and build a new string from them, and you will know why every string method hands you a new value instead of changing the old one.

Write the type in lowercase, string. The capitalized String is the legacy wrapper object and is almost never what you want.

Three quoting styles

const single = 'hello';
const double = "hello";
const tick = `hello`;

Single and double quotes are interchangeable, so pick one and stay consistent. Backticks make a template literal, which can interpolate expressions and span several lines:

const item: string = "tea";
const price: number = 3.5;
console.log(`${item} costs ${price * 2} for two`); // tea costs 7 for two

The everyday methods

const s: string = "  Hello, World  ";

s.length;                // 16, a property: no parentheses
s.trim();                // "Hello, World"
s.trim().toUpperCase();  // "HELLO, WORLD"
s.trim().toLowerCase();  // "hello, world"
s.includes("World");     // true
s.indexOf("World");      // 9, or -1 when absent
s.trim().slice(7);       // "World": from index 7 to the end
s.trim().slice(0, 5);    // "Hello": from 0 up to, not including, 5
s.trim().replace("World", "TS"); // "Hello, TS"
"7".padStart(3, "0");    // "007"
"ab".repeat(3);          // "ababab"

Indexes start at 0. slice(a, b) includes a and excludes b, and a b past the end is simply clamped.

Reading one character

"hello".charAt(0);   // "h"
"hello"[0];          // "h"
"".charAt(0);        // ""         (an empty string: safe)
""[0];               // undefined  (not a string at all)

Bracket indexing returns undefined when the index is out of range, and calling a method on undefined throws a TypeError. charAt always returns a string, so on possibly empty text it is the safer choice.

The trap: strings are immutable

No string method changes the string in place. Every method returns a NEW string:

let label = "draft";
label.toUpperCase();       // the result is thrown away
console.log(label);        // still "draft"

label = label.toUpperCase();
console.log(label);        // "DRAFT": you must keep the return value

Split, change, join

split(separator) cuts a string into an array of pieces, and join(glue) glues an array back into a string. To change every piece, map calls a function on each element and collects the results into a new array:

const title: string = "Hello World Wide Web";
const pieces: string[] = title.split(" ");     // ["Hello", "World", "Wide", "Web"]
const shouted: string[] = pieces.map(p => p + "!"); // ["Hello!", "World!", "Wide!", "Web!"]
console.log(shouted.join(", "));               // Hello!, World!, Wide!, Web!

p => p + "!" is a tiny function written inline: it receives each piece as p and returns that piece with ! added. When the function needs several steps, its body goes in braces and ends with return (the function-types lesson covers functions in full).

Splitting on one space gives an empty string wherever two spaces touch: "a b".split(" ") is ["a", "", "b"], and joining with the same single space puts both spaces back. Splitting on a pattern like /\s+/ instead swallows the extra spaces for good.

One caveat for later: split("") cuts between UTF-16 code units, so emoji and some non-Latin characters get cut in half. For ordinary letters it is exact.

Common mistakes

  • Discarding the return value. word.toUpperCase(); on its own line changes nothing.
  • name[0].toUpperCase() on an empty string. ""[0] is undefined, so this throws TypeError: Cannot read properties of undefined. charAt(0) is safe.
  • Fixing only the first character. Upper-casing the start of "hELLO" gives "HELLO", not "Hello"; the rest needs its own change.
  • Cutting at the wrong index. line.slice(space) starts AT the space, so the second name keeps a leading space. Start one position later.

Your exercise

Make a name tag from a first and last name. The starter reads and trims the line into line; the two names are separated by exactly one space, in any mix of upper and lower case.

Find the space with indexOf, then cut the first name out with slice(0, space) and the last name with a slice that starts one position after the space. Normalize each name to lower case first, then build the title-case versions from the lower-case ones: the first character upper-cased (charAt(0) is safe even on a one-letter name) joined to the rest, slice(1). The initials and the username are built from the pieces you already have.

Remember that strings are immutable: every method returns a new string, so keep each result in a const. The mistakes the hidden tests catch are the ones above: upper-casing the first letter but forgetting to lower-case the rest, and a second name that keeps its leading space.

Up nextInterfaces and Object TypesStrings and Interfaces

Discussion

Ask a question, share an insight, or help someone who’s stuck.

Sign in to post a comment or reply.

Loading…