1. Get union of keys of T:
keyof T produces a string (or symbol) union of property names, commonly paired with indexed access like T[K].
type User = { id: string; name: string };
type Keys = keyof User; // 'id' | 'name'Get the Preplance app for a seamless learning experience. Practice offline, get daily streaks, and stay ahead with real-time interview updates.
Get it on
Google Play
4.9/5 Rating on Store
Typescript · Question Set
Interfaces & Utils interview questions for placements and exams.
Questions
14
Included in this set
Subject
Typescript
Explore more sets
Difficulty
Mixed
Level of this set
Go through each question and its explanation. Use this set as a focused practice pack for Typescript.
keyof T produces a string (or symbol) union of property names, commonly paired with indexed access like T[K].
type User = { id: string; name: string };
type Keys = keyof User; // 'id' | 'name'For complete preparation, combine this set with full subject-wise practice for Typescript. You can also explore other subjects and sets from the links below.
Compatibility is about shape. If two types have the same required members, values are assignable between them—names don’t need to match.
type A = { x: number };
interface B { x: number }
const a: A = { x: 1 };
const b: B = a; // shape-compatiblePartial<T> flips every property in T to optional—perfect for patch/update payloads.
type User = { id: string; name: string };
type UserUpdate = Partial<User>; // { id?: string; name?: string }Record<K, V> builds an object type where keys come from union K and each value is V—great for dictionaries.
type Route = 'home' | 'about';
const paths: Record<Route, string> = { home: '/', about: '/about' };ReadonlyArray<T> allows reading (map, slice, reduce) but blocks mutation (no push/pop). Perfect for API inputs.
function total(nums: ReadonlyArray<number>) { return nums.reduce((a,b)=>a+b,0); }Parameters<T> gives the parameter tuple type of a function. ConstructorParameters<T> does the same for class constructors.
function f(a: string, b: number) {}
type P = Parameters<typeof f>; // [string, number]Readonly prevents accidental changes on read models; Pick/Omit selects allowed fields; Partial makes them optional for updates. Result: strict, self-documenting DTOs that block unwanted properties at compile time.
type User = { id: string; name: string; email: string; role: 'admin'|'user' };
// client reads
type UserView = Readonly<Pick<User, 'id'|'name'|'email'>>;
// client updates (only allowed fields, all optional)
type UserUpdate = Partial<Pick<User, 'name'|'email'>>;Pick<T, K> keeps only K from T. The opposite is Omit<T, K>, which drops K from T.
type User = { id: string; name: string; email: string };
type UserPreview = Pick<User, 'id' | 'name'>;NonNullable<T> is a shorthand for excluding null and undefined. It guarantees a defined value.
type MaybeStr = string | null | undefined; type Str = NonNullable<MaybeStr>; // string
Interfaces with the same name merge into one. Type aliases cannot merge—redeclaring the same type name is an error.
interface Box { id: string }
interface Box { size: number }
// Merged: { id: string; size: number }Interfaces extend and merge naturally and work cleanly with classes. Use type aliases for unions, intersections, and advanced mapped/conditional types.
interface Animal { speak(): void }
class Dog implements Animal { speak() { /*...*/ } }Interfaces: best for public object shapes and class contracts; they extend and merge naturally. Types: best for unions, intersections, and complex transformations. Use interface when you want merging/extensibility; use type when modeling unions or composing with mapped/conditional types.
interface A { x: number }
interface A { y: number } // merged
const a: A = { x: 1, y: 2 };
type B = { x: number } & { y: number };
const b: B = { x: 1, y: 2 };keyof defines allowed keys, T[K] gives their value types, and Record<K, V> maps keys to values. Together they enforce key correctness and keep value types in sync—no stringly-typed lookups.
type User = { id: string; active: boolean };
function pick<T, K extends keyof T>(obj: T, keys: K[]): Record<K, T[K]> {
const out = {} as Record<K, T[K]>;
for (const k of keys) out[k] = obj[k];
return out;
}
const u = { id: 'u1', active: true };
const subset = pick(u, ['id']); // { id: string }Add a .d.ts file that reopens the module with declare module and extends its interfaces. This avoids editing node_modules and survives package upgrades.
/* types/my-lib-augment.d.ts */
declare module 'my-lib' {
interface Widget { version: string }
export function makeWidgetWithVersion(v: string): Widget;
}
// Usage
import { makeWidgetWithVersion } from 'my-lib';
const w = makeWidgetWithVersion('1.2.3');
w.version.toUpperCase();