TubeReads

TypeScript, C# and Turbo Pascal with Anders Hejlsberg

How does one person create three of the most widely used programming languages in history? Anders Hejlsberg shaped developer productivity for decades, from Turbo Pascal in the 1980s to C# and TypeScript today. Yet the path to each language was rarely straightforward: C# might never have existed without a lawsuit, TypeScript's open-sourcing was a battle inside old Microsoft, and each language took roughly a decade to mature. What does 40 years of designing languages and tools teach about building for developers—and how might AI fundamentally reshape that craft?

Durée de la vidéo : 1:16:02·Publié 13 mai 2026·Langue de la vidéo : English
15–16 min de lecture·14,249 mots prononcésrésumé en 3,080 mots (5x)·

1

Points clés

1

The most successful programming languages are inseparable from their tooling. From Turbo Pascal's blazing speed and interactive IDE to TypeScript's tight VS Code integration, the compiler alone is never the product—the entire edit-compile-run-debug cycle is.

2

Language design is a 10-year cycle. Version one has issues, version two fixes them, version three is finally great, and only then do you convince people to adopt it. Betting on a new language requires long-term commitment that most companies and developers underestimate.

3

TypeScript succeeded because it added an erasable type system to JavaScript purely to enable better tooling—not for runtime performance. The productivity boost came from statement completion, refactoring, and go-to-definition, not from the types themselves.

4

AI is turning developers into project managers overseeing an army of junior programmers. The craft is shifting from writing code to reviewing, architecting, and ensuring semantic correctness—but determinism still requires programming languages, not just stochastic models.

5

Small, expert teams design the best languages. The C# design group was just six to seven people who met three times a week for two hours, all with prior language-building experience. Their job was to critique each other's ideas until only the strongest survived.

En bref

Programming languages succeed or fail based on the complete developer experience, not just syntax. Anders Hejlsberg's 40-year career reveals that great tools require integrated IDEs, a 10-year commitment to maturity, and a willingness to evolve. In the AI era, developers are shifting from writing code to reviewing and architecting it—but the need for determinism, locality, and semantic understanding means languages and tooling will matter more than ever.


2

From High School HP to Compiler ROMs

How a Danish teenager's access to a 32K ferrite-core HP 2100 sparked a 40-year language design career.

Anders Hejlsberg's journey into programming began in mid-to-late 1970s Copenhagen, where his high school offered students rare access to a Hewlett-Packard 2100 computer with 32 kilobytes of ferrite-core memory. The machine was so primitive it had no ROM; the bootloader had to be loaded from paper tape every time it started. Students programmed in Fortran, a slow BASIC interpreter, and Algol—HP's version of which lacked recursion support because the call instruction stored the return address in the first word of the subroutine.

By 1979, Hejlsberg had moved to the Danish Technical University and co-founded Denmark's first computer retail store, selling kit computers like the Z80-based NASCOM, Apple IIs, and Commodore 64s. He wrote a Pascal compiler that fit into a 12-kilobyte ROM, a precursor to Turbo Pascal. The key insight was already present: a programming language is not just a compiler, but an entire experience—editing, compiling, running, and debugging must fit together seamlessly.


3

Why Turbo Pascal Was Turbo

Speed
«Turbo» meant fast—this was the era of Audi Quattros and turbocharged engines. The compiler was blazingly fast and super interactive, bridging the gap between interpreted BASIC and compiled Pascal.
💰
Price
Turbo Pascal sold for $49.95 when competitors charged $500 for compilers alone. The price was so low that piracy was minimal—people joked about the «Russian site license» where one copy was sold and copied everywhere.
📦
Complete Experience
It wasn't just a compiler. Turbo Pascal included an editor, runtime library, and later a debugger. The entire edit-compile-run cycle was integrated and interactive, unlike competitors that required swapping floppy disks for different compiler passes.
🎯
Smart Debugging
Early versions printed the memory address of runtime errors. The compiler could then stop at that address and show the corresponding source line—no line maps or debuggers needed, just clever reuse of the compiler itself.

4

The Sun Lawsuit That Created C#

Microsoft's Java tools were enjoined by a judge, forcing a pivot to a homegrown language.

Anders Hejlsberg joined Microsoft in 1996 to architect the company's Java development tools, working on Visual J++ 6.0. Microsoft built a class library (WFC) that allowed developers to create Windows desktop apps in Java, but the Sun Microsystems lawsuit changed everything. A judge in San Jose effectively ended Visual J++ as a viable product—no company would bet on a language that had been legally enjoined.

The lawsuit, combined with Microsoft's realization that licensing core technology from a competitor was strategically unsound, sparked the creation of .NET and C#. Microsoft wanted a language that rolled up the ease of Visual Basic with the power of C++, added garbage collection and exception handling, and introduced modern features like a unified object system with reflection. The design goal was explicit: create something that could compete with Java while giving developers both productivity and performance. C# launched as part of a simultaneous effort with the .NET runtime, designed from day one to be language-agnostic and standardized.


5

The 10-Year Language Cycle

Version one has issues, version two fixes them, version three is great—then you convince people.

💡

The 10-Year Language Cycle

Programming languages operate on a fundamentally different timescale than most software. Version one is great but has issues. Version two addresses those issues. Version three is finally truly great. And only then do you begin the long process of convincing people to adopt it. The entire cycle takes at least a decade. This applies to Turbo Pascal, C#, and TypeScript alike—and it's a reality that most companies and developers underestimate when betting on a new language.


6

Designing C# in a Room of Six

A small expert team met three times a week to critique ideas until only the strongest survived.

1

Assemble a Small Expert Team The C# design group had six to seven people, all of whom had built or worked on programming languages before. They knew what worked and what didn't.

2

Meet Regularly, Discuss Deeply The team met three times a week for two hours. They could jump straight into technical discussions without spending an hour level-setting, because everyone was already deeply familiar with the problem space.

3

Critique Every Idea When someone proposed a new feature, the group's job was to shoot it down. If an idea could withstand the criticism, it was probably good. This adversarial review process filtered out weak designs.

4

Specify in Parallel Anders wrote the language specification in parallel with the design meetings. This kept the design grounded and ensured that ideas were fleshed out in writing, not just discussed abstractly.

5

Build Two Implementations A compiler team implemented C# in C++, and a separate language service provided syntax coloring and statement completion. Over time, maintaining two implementations became a drag, leading eventually to the Roslyn project, which unified both into a single self-hosted compiler.


7

«We Knew We Wanted to Build an Object-Oriented Language»

C#'s design goals were clear from day one: power, productivity, and a unified object system.

We knew we wanted to build an object-oriented language. We wanted managed code or bytecode so we could target different runtime environments. We wanted garbage collection and exception handling, but also things like a unified object system where anything can be assigned to an object and if it's a value type we box it. And reflection—you can ask an object, «What are you?» and get all of the facts about it at runtime and dynamically manipulate it in ways that just don't exist in a lot of other environments.

Anders Hejlsberg


8

TypeScript: Fixing JavaScript Without Breaking It

A Microsoft team realized the best cross-platform language wasn't Java—it was JavaScript.

In the early 2000s, the world woke up to the fact that JavaScript, not Java, was the true cross-platform language. Google's V8 engine made JavaScript performant, HTML5 was ratified, and the iPhone triggered a device revolution. Every platform ran a browser with JavaScript. Microsoft's Outlook.com team came to the C# group asking them to productize Script#, a cross-compiler that turned C# into JavaScript. The request was revealing: developers wanted «a grownup programming language with grownup tooling»—Visual Studio, projects, statement completion, refactoring.

Anders and Steve Lucco proposed a better approach: fix JavaScript itself. JavaScript is a decent little language—Brendan Eich got functional programming right, and functions as first-class objects are a godsend—but it lacks a type system. Without types, you cannot build great tooling at scale. The insight was to create a superset of JavaScript that added an erasable type system. TypeScript would compile away the types, but the types would enable Visual Studio-class tooling: statement completion, go-to-definition, find-all-references, and refactoring. The productivity boost came entirely from better tools, not from runtime performance.


9

The Open-Source Battle Inside Old Microsoft

TypeScript had to be open source, but getting approval inside Ballmer-era Microsoft took real effort.

THE REALITY
Zero Chance Without Open Source
The TypeScript team knew with absolute certainty that the JavaScript ecosystem would never adopt a proprietary language licensed from Microsoft. Open source was non-negotiable. Developers were voting with their feet, and Microsoft's old DNA was pulling in the opposite direction.
THE COMPROMISE
Codeplex Tax, Then GitHub Freedom
TypeScript launched as open source in 2012—but on Microsoft's own Codeplex repository, where no one was. For two years, it was «crickets.» In 2014, the team moved to GitHub, and everything changed. Open development replaced open source in name only. The entire workflow—issues, PRs, discussions—moved to GitHub, and TypeScript adoption exploded.

10

Why TypeScript Beat the Alternatives

Better tooling, backed by a type system that didn't force you to type everything.

TypeScript became the most popular language on GitHub in November 2025, according to the Octoverse report. The reason is straightforward: tooling. Developers adopted TypeScript because it gave them statement completion, refactoring, go-to-definition, and find-all-references at scale—all powered by a type system that the runtime never sees. Other languages tried to compete (CoffeeScript, and many others targeted JavaScript), but TypeScript had two advantages.

First, it was a true superset of JavaScript—any valid JavaScript is valid TypeScript. Second, it combined explicit types where context is missing with type inference where context exists. This balance is critical: forcing developers to annotate every variable would make the language verbose and error-prone (especially for AI, which would have to track and repeat types constantly). But inference alone isn't enough for large codebases or tooling. TypeScript hit the sweet spot, and the fact that it was built in lockstep with VS Code—another open-source Microsoft project—created a symbiotic relationship that reinforced both products. The language and the IDE evolved together, just as they had with Turbo Pascal decades earlier.


11

Building an Interactive Compiler

🔍
Scanner and Parser
Like most compilers, TypeScript starts with a lexer (scanner) that turns text into tokens, then a parser that builds abstract syntax trees. These stages are standard.
🔗
Binder
The binder builds symbol tables and attaches them to functions, enabling name lookups. It also constructs a control-flow graph, which helps the type checker reason about code paths.
Type Checker
The largest part of the pipeline. It checks that types relate correctly, that you're assigning the right thing to the right thing, and that you're calling something that exists.
⚙️
Emitter
The emitter erases type annotations and can down-level newer ECMAScript features to older syntax. Today, with evergreen browsers, downleveling is less critical—the emitter mostly just strips types.
Interactive Mode
The compiler functions as an IDE service. If you have 500,000 lines of code in 500 files, it only re-parses the file you're editing. It lazily resolves types just enough to answer the current query (e.g., statement completion), all within 200 milliseconds.

12

Gradual Typing: The Secret Weapon

TypeScript doesn't require 100% correctness, which unlocks language features no other system can provide.

💡

Gradual Typing: The Secret Weapon

TypeScript's gradual typing—types are optional and erased at runtime—is unlike almost any other programming language. Because the types exist purely for tooling and checking, not for code generation, TypeScript doesn't have to prove 100% correctness. In a structural type system with recursive types, some cases are infinitely recurring. But TypeScript can say, «We've proven it to four levels—that's probably good enough.» You can't do that if you're generating machine code, where indeterminate behavior is unacceptable. But JavaScript already has a well-defined runtime, so checking 99% instead of 0% is a massive win—and it enables features no other language can provide.


13

Async/Await: The Compiler Writes the State Machine

Cooperative multitasking is hard to code by hand, so the compiler does it for you.

Many languages are built around cooperative multitasking: an event loop dispatches events, you handle them, then yield back to the loop. The problem is long-running work. How do you pause in the middle, yield to the event loop, and resume when your result is ready? You have to build a state machine—move all your state off the stack into heap-allocated objects, add a big switch statement to track where you are, and handle continuation logic manually. It's a nightmare.

Async/await solves this by letting the compiler write the state machine for you. The «await» keyword says, «I want to yield here, and when this promise completes, resume here.» The compiler transforms your sequential code into a state machine automatically. This is why async/await spread so quickly to JavaScript, Python, Rust, and other languages. The tradeoff is function coloring—async functions and regular functions are incompatible, and once a function is async, everything that calls it must be async. Some environments like Go avoid this with green threads (lightweight, language-emulated threads), but for languages with existing event loops, async/await was the right solution.


14

AI Is Turning Developers Into Project Managers

The craft is shifting from writing code to reviewing and architecting it.

Anders Hejlsberg sees developers increasingly becoming project managers who oversee an army of junior programmers called AI agents. The agents spit out reams of code, but someone has to have the big picture, review the output, and build the architecture. It's a different kind of craft and a different kind of enjoyment. Anders has always liked writing code—seeing it work is fulfilling—and AI robs a bit of that.

But he believes the review process can be made more interesting. Today, code reviews are a list of diffs in alphabetical order, and you make heads or tails of it. More pedagogical presentations are possible: AI-generated commentary that explains changes and guides you through the logic. The symbiotic relationship between human and AI needs work to keep the enjoyment in the craft. But one thing is certain: you cannot absolve yourself from understanding what's going on. Vibe coding works until it doesn't, and when the AI goes off track and you can't fix it, you're stuck. Responsibility lies with the programmer, not the AI. You can't fire the AI. Ultimately, AI is a tool to make developers more productive, but it will fundamentally change how programs are written.


15

Why Languages Matter More in the AI Era

AI needs determinism, and only programming languages provide that.

THE PROBLEM
AI Is Stochastic, Apps Are Deterministic
AI is inherently non-deterministic—it might give a different answer the next time you ask the same question, either due to randomness, a new model, or updated training data. But we can't build applications with non-deterministic behavior. A banking app that hallucinates is not acceptable. At some point, the rubber meets the road, and you need something you can reason about and replicate.
THE SOLUTION
Ask AI to Write the Program, Not Compute the Answer
Don't ask AI for the answer—ask it to write a program that computes the answer. Programming languages provide the determinism that AI lacks. This is why AI agents increasingly write Python scripts when working with data: they know the final step must be deterministic. Languages remain the bridge between stochastic models and reliable execution.

16

What Makes a Language AI-Friendly?

🏷️
Types + Inference
AI has seen the most JavaScript, TypeScript, and Python in its training sets, so it does best with those. But types help guide AI to better programs, and inference reduces verbosity. TypeScript's balance is ideal: type the outer parameters, infer everything else.
📍
Locality
Avoid globals and ambiguous scope. AI struggles with languages where it has to grok the entire program to understand one file. Good module systems and clear imports reduce context-window size and make summarization easier.
🔎
Semantic Services
AI is starting to use language services (LSP) to find references, rename symbols, and navigate code. But semantic search is critical—a property named «address» could be anywhere. Language services that understand scope and types will become increasingly important.
Performance
Faster feedback loops matter. AI benefits from fast compilers and language servers that keep projects «hot» in memory, providing instant LSP queries. When the AI stops asking for 10 minutes, the server can dump the project.

17

Porting TypeScript to Native Code

A year and a half of work to move the compiler from JavaScript to Go.

The TypeScript team has spent the last year and a half porting the compiler from JavaScript to native code (Go). Early in the project, AI was nowhere near capable enough to help, but as the port progressed, AI became increasingly useful. Today, the team uses AI to code-review pull requests (which has gotten much better), implement or fix simple issues, and port backlogged PRs from the old codebase to the new native compiler.

AI also handles drudgery work: «Here's this feature. Write me tests in the same style as these other tests.» No one likes writing tests, but AI loves it and will pump out hundreds. The team uses AI to eliminate toil. But they are not at a point where AI absolves them from understanding what they're doing. When it comes to implementing new language features, figuring out how types, symbols, binding, and parsing relate, or choosing the most efficient data structure, AI isn't quite there yet. The TypeScript codebase is one big brownfield, and there are only so many compilers in AI training sets—unlike the gazillion React apps AI has seen.


18

The Book That Shaped a Career

Niklaus Wirth's «Programs + Data Structures = Algorithms» from the 1970s, still relevant today.

I always recommend the same book, which is Niklaus Wirth's «Programs + Data Structures = Algorithms.» It was written in the '70s, but it was a revelation for me. This is how I learned about hash tables and how to construct a small compiler. It was very light on symbolism and very rich on examples. I was always an engineer, so that book just appealed to me, and I think it's still super relevant today.

Anders Hejlsberg


19

The Product Is the Experience, Not the Compiler

From Turbo Pascal to TypeScript, the lesson is the same: tooling and language are inseparable.

💡

The Product Is the Experience, Not the Compiler

Anders Hejlsberg has spent 40 years building programming languages, and the through-line is clear: the compiler is never the product. The product is the whole experience—editing, compiling, running, debugging, and the runtime library. Turbo Pascal succeeded because it integrated everything. C# succeeded because it came with Visual Studio and the .NET framework. TypeScript succeeded because it was built in lockstep with VS Code. Developers care about being productive and being «in the zone,» where the tool is an extension of their fingertips. That's why developers become so attached to their languages and tools—it's where they spend the majority of their working life. Language designers who ignore tooling are building half a product.


20

Personnes

Anders Hejlsberg
Creator of Turbo Pascal, Delphi, C#, and TypeScript; Technical Fellow at Microsoft
guest
Gergely Orosz
Host, The Pragmatic Engineer Podcast
host
Steve Lucco
Co-inventor of TypeScript; Technical Fellow at Microsoft
mentioned
Brendan Eich
Creator of JavaScript
mentioned
Niklaus Wirth
Computer scientist, author of «Programs + Data Structures = Algorithms»
mentioned

Glossaire
Ferrite-core memoryAn early form of computer memory using tiny magnetic rings (cores) threaded with wires; you could literally see the cores inside the machine.
BytecodeAn intermediate representation of a program that is platform-independent and executed by a virtual machine or runtime, rather than compiled directly to machine code.
Garbage collectionAutomatic memory management where the runtime reclaims memory that is no longer in use, freeing developers from manual memory allocation and deallocation.
Language Server Protocol (LSP)A standardized protocol that allows IDEs and editors to communicate with language servers, providing features like auto-completion, go-to-definition, and error checking.
Gradual typingA type system where types are optional; code can be dynamically typed (like JavaScript) or statically typed (with annotations), and the two coexist in the same codebase.
Function coloringThe problem in async/await systems where async functions and regular functions are incompatible: once a function is async, all callers must also be async, creating two «colors» of functions.
Green threadsLightweight threads managed by a language runtime rather than the operating system, allowing thousands of concurrent tasks without the overhead of OS threads.
Abstract Syntax Tree (AST)A tree representation of the syntactic structure of source code, where each node represents a construct (e.g., expression, statement) occurring in the code.

Avertissement : Ceci est un résumé généré par IA d'une vidéo YouTube à des fins éducatives et de référence. Il ne constitue pas un conseil en investissement, financier ou juridique. Vérifiez toujours les informations auprès des sources originales avant de prendre des décisions. TubeReads n'est pas affilié au créateur de contenu.