Type Conversions in Dart
last modified May 25, 2025
Dart is a statically typed language with a sound type system that handles type conversions differently than dynamically typed languages. This tutorial covers Dart's type conversion system including explicit casting, parsing, and conversion methods.
Dart Type Conversion Overview
Dart's type conversion system is designed to be explicit and type-safe. It allows you to convert between compatible types while preventing implicit conversions that could lead to runtime errors. The main conversion techniques include explicit casting, number parsing, string conversion, and type promotion.
| Conversion Type | Description | Example |
|---|---|---|
| Explicit Casting | Using as operator for type assertions |
var str = obj as String; |
| Number Parsing | Converting strings to numbers | int.parse('42') |
| String Conversion | Converting to string representation | 123.toString |
| Type Promotion | Automatic in control flow | if (obj is String) {...} |
Key points about Dart casting:
- Use
asfor explicit type assertions - Will throw
TypeErrorif types are incompatible - Always check types with
isbefore casting when uncertain - No implicit conversions between unrelated types
Explicit Type Casting
Dart uses the as operator for explicit type casting between
compatible types.
void main() {
dynamic value = 'Hello Dart';
// Safe casting with 'as'
String str = value as String;
print('String length: ${str.length}');
// This would throw TypeError at runtime:
// int number = value as int;
// Safe casting with type check
if (value is String) {
print('Uppercase: ${value.toUpperCase()}');
}
}
In Dart, casting is explicit and requires the as operator. This
allows you to assert that a value is of a specific type. If the value is not
compatible with the target type, a TypeError will be thrown at
runtime.
$ dart run casting.dart String length: 10 Uppercase: HELLO DART
Number Parsing and Conversion
Dart provides several ways to convert strings to numbers and between numeric types.
void main() {
// String to number
int intVal = int.parse('42');
double doubleVal = double.parse('3.14');
// Number to string
String intStr = 42.toString();
String doubleStr = 3.14159.toStringAsFixed(2);
// Between numeric types
double d = 5; // int to double
int i = 3.14.toInt(); // double to int (truncates)
print('Parsed int: $intVal');
print('Parsed double: $doubleVal');
print('Int to string: $intStr');
print('Formatted double: $doubleStr');
print('Double to int: $i');
// Safe parsing with tryParse
int? maybeInt = int.tryParse('abc');
print('TryParse result: $maybeInt');
}
The int.parse and double.parse methods convert
strings to their respective numeric types. If the string cannot be parsed,
a FormatException will be thrown. To avoid this, you can use
tryParse, which returns null if parsing fails.
The toString method converts numbers to their string
representation. You can also use toStringAsFixed to format
decimal places, and toInt or toDouble to convert
between numeric types. Dart does not allow implicit conversions between
numeric types, so you must use these methods explicitly.
$ dart run number_conversion.dart Parsed int: 42 Parsed double: 3.14 Int to string: 42 Formatted double: 3.14 Double to int: 3 TryParse result: null
String Conversion
Converting values to strings in Dart is straightforward with several options available.
void main() {
// Basic toString()
String intStr = 42.toString();
String boolStr = true.toString();
// String interpolation automatically calls toString()
String interpolated = 'Value: ${123}, Bool: ${false}';
// More complex formatting
String pi = 3.14159.toStringAsFixed(2);
String hex = 255.toRadixString(16);
print('intStr: $intStr');
print('boolStr: $boolStr');
print('interpolated: $interpolated');
print('pi: $pi');
print('hex: $hex');
}
The toString method is available on all objects in Dart, allowing
you to convert any value to its string representation. Dart also supports string
interpolation, which automatically calls the toString method on
objects when used within a string. This makes it easy to create formatted
strings from various types.
$ dart run string_conversion.dart intStr: 42 boolStr: true interpolated: Value: 123, Bool: false pi: 3.14 hex: ff
Type Promotion in Dart
Dart automatically promotes types in certain control flow situations, providing type safety without explicit casting.
void main() {
dynamic value = 'Dart';
// Type promotion in conditionals
if (value is String) {
print('Length: ${value.length}'); // value is now String
}
// Promotion with null checks
String? maybeString;
if (maybeString != null) {
print('Length: ${maybeString.length}'); // maybeString is non-null
}
// Promotion with logical operators
Object obj = 'Hello';
if (obj is String && obj.length > 3) {
print('Long string: $obj');
}
}
Dart's type promotion works in is type checks,
Null checks (!= null, == null),
Logical expressions (&&, ||), and
after exception catches.
$ dart run type_promotion.dart Length: 4 Long string: Hello
Working with Collections
Dart provides methods to convert between different collection types.
import 'dart:collection';
void main() {
// List conversions
List<int> numbers = [1, 2, 3];
List<String> strings = numbers.map((n) => n.toString()).toList();
// Set from List
Set<int> uniqueNumbers = numbers.toSet();
// Map from List
Map<int, String> map = {for (var n in numbers) n: 'Number $n'};
// Convert to different collection types
var fixedList = List<int>.unmodifiable(numbers);
var linkedHashSet = LinkedHashSet<int>.from(numbers);
print('Strings: $strings');
print('Unique numbers: $uniqueNumbers');
print('Map: $map');
print('Fixed List: $fixedList');
print('LinkedHashSet: $linkedHashSet');
}
The toList, toSet, and map methods
provide convenient ways to convert between collections in Dart. You can also
create new collections using constructors like List.from and
Set.from.
$ dart run collection_conversion.dart
Strings: [1, 2, 3]
Unique numbers: {1, 2, 3}
Map: {1: Number 1, 2: Number 2, 3: Number 3}
Fixed List: [1, 2, 3]
LinkedHashSet: {1, 2, 3}
JSON Serialization
Dart provides built-in support for converting objects to/from JSON.
import 'dart:convert';
// Custom objects need toJson/fromJson methods
class Language {
final String name;
final double version;
Language(this.name, this.version);
Map<String, dynamic> toJson() => {'name': name, 'version': version};
factory Language.fromJson(Map<String, dynamic> json) {
return Language(json['name'], json['version']);
}
}
void main() {
// Convert to JSON
Map<String, dynamic> data = {'name': 'Dart', 'version': 2.19, 'isCool': true};
String jsonStr = jsonEncode(data);
// Parse from JSON
Map<String, dynamic> decoded = jsonDecode(jsonStr);
print('Original: $data');
print('JSON: $jsonStr');
print('Decoded: $decoded');
Language dart = Language('Dart', 2.19);
String langJson = jsonEncode(dart);
Language decodedLang = Language.fromJson(jsonDecode(langJson));
print('Language JSON: $langJson');
print('Decoded language: ${decodedLang.name} ${decodedLang.version}');
}
The dart:convert library provides methods for JSON
serialization and deserialization. It allows you to easily convert
Dart objects to JSON strings and parse JSON strings back into Dart objects.
You can use the jsonEncode and jsonDecode
methods for basic types, lists, and maps. For custom classes, you need to
implement toJson and fromJson methods to
handle serialization and deserialization. It works with primitive types,
lists, and maps out of the box.
$ dart run json_conversion.dart
Original: {name: Dart, version: 2.19, isCool: true}
JSON: {"name":"Dart","version":2.19,"isCool":true}
Decoded: {name: Dart, version: 2.19, isCool: true}
Language JSON: {"name":"Dart","version":2.19}
Decoded language: Dart 2.19
Source
Dart Type System
Dart Language Tour: Conversion
Dart's type conversion system provides both safety through static typing and flexibility through explicit conversion methods. Understanding these conversion techniques is essential for writing robust Dart applications.
Author
List all Dart tutorials.