Andrew J. Pounds, Ph.D.
After completing this exercise, you will be able to:
std.stdioif, else, switch)while, do-while, and forD is a multi-paradigm systems programming language created by Walter Bright at Digital Mars and released in 2001. It was developed by re-engineering C++, offering modern features while maintaining efficiency and the ability to interface directly with hardware and system APIs.
D supports multiple programming paradigms including:
D source files use the .d extension. We will use the GNU D Compiler (GDC), which is a front-end for the GCC back-end.
Create a file called hello.d with the following content:
import std.stdio;
void main() {
writeln("Hello, World!");
}
Open a terminal and navigate to the directory containing your file. Compile and run with:
gdc hello.d -o hello
./hello
You should see Hello, World! printed to the console.
-o hello option, GDC will create an executable called a.out by default.
| Code Element | Explanation |
|---|---|
import std.stdio; |
Imports the standard I/O module from D's standard library (Phobos) |
void main() |
The entry point of the program; void means no return value |
writeln(...) |
Writes output to the console followed by a newline |
D is a statically typed language, meaning you must declare the type of each variable. D provides a rich set of fundamental types:
| Type | Size | Range |
|---|---|---|
byte |
8 bits | -128 to 127 |
short |
16 bits | -32,768 to 32,767 |
int |
32 bits | -2,147,483,648 to 2,147,483,647 |
long |
64 bits | -9.2×1018 to 9.2×1018 |
Each signed type has an unsigned counterpart: ubyte, ushort, uint, ulong.
| Type | Size | Description |
|---|---|---|
float |
32 bits | Single precision (~7 significant digits) |
double |
64 bits | Double precision (~15 significant digits) |
real |
80+ bits | Highest precision available on the platform |
| Type | Description | Example |
|---|---|---|
bool |
Boolean (true or false) | bool flag = true; |
char |
Single UTF-8 code unit | char letter = 'A'; |
string |
Immutable array of characters | string name = "Alice"; |
autoD can infer types automatically using the auto keyword:
import std.stdio;
void main() {
// Explicit type declarations
int age = 25;
double gpa = 3.85;
string name = "Alice";
bool enrolled = true;
// Type inference with auto
auto count = 100; // inferred as int
auto pi = 3.14159; // inferred as double
auto greeting = "Hi"; // inferred as string
writeln("Name: ", name);
writeln("Age: ", age);
writeln("GPA: ", gpa);
writeln("Enrolled: ", enrolled);
}
The std.stdio module provides four primary output functions:
| Function | Description |
|---|---|
write() |
Outputs without adding a newline |
writeln() |
Outputs and adds a newline at the end |
writef() |
Formatted output without newline |
writefln() |
Formatted output with newline |
import std.stdio;
void main() {
int x = 42;
double price = 19.99;
string item = "widget";
// Basic output
writeln("The answer is ", x);
// Multiple values
writeln("Item: ", item, ", Price: $", price);
// Using write (no newline)
write("Processing");
write("...");
writeln(" Done!");
// Formatted output
writefln("The %s costs $%.2f", item, price);
writefln("Hex: %x, Padded: %05d", x, x);
}
| Specifier | Description | Example Output |
|---|---|---|
%d |
Integer (decimal) | 42 |
%f |
Floating-point | 3.141593 |
%.2f |
Float with 2 decimal places | 3.14 |
%s |
String (or any type) | hello |
%x |
Hexadecimal | 2a |
%05d |
Zero-padded to 5 digits | 00042 |
Reading input in D requires the readln() function and typically the std.string and std.conv modules for processing:
import std.stdio;
import std.string; // for strip()
import std.conv; // for to!int(), to!double()
void main() {
// Reading a string
write("Enter your name: ");
string name = readln().strip();
// Reading an integer
write("Enter your age: ");
int age = to!int(readln().strip());
// Reading a double
write("Enter your GPA: ");
double gpa = to!double(readln().strip());
writefln("Hello, %s! Age: %d, GPA: %.2f", name, age, gpa);
}
readln() function includes the newline character in the returned string. Always use .strip() to remove leading and trailing whitespace (including the newline) before processing.
readln() reads a line of text from the console (including the newline).strip() removes the trailing newline and any extra whitespaceto!int() or to!double() converts the string to a numberThe assignment operator = stores a value in a variable:
int x = 10; // declare and initialize
x = 20; // assign new value
int y = x; // copy value from x to y
| Operator | Description | Example | Result (if a=10, b=3) |
|---|---|---|---|
+ |
Addition | a + b |
13 |
- |
Subtraction | a - b |
7 |
* |
Multiplication | a * b |
30 |
/ |
Division | a / b |
3 (integer division) |
% |
Modulus (remainder) | a % b |
1 |
int x = 10;
x += 5; // x = x + 5 → x is now 15
x -= 3; // x = x - 3 → x is now 12
x *= 2; // x = x * 2 → x is now 24
x /= 4; // x = x / 4 → x is now 6
x %= 4; // x = x % 4 → x is now 2
int count = 5;
count++; // count is now 6 (post-increment)
++count; // count is now 7 (pre-increment)
count--; // count is now 6 (post-decrement)
--count; // count is now 5 (pre-decrement)
import std.stdio;
void main() {
writeln(7 / 2); // prints 3 (integer division)
writeln(7.0 / 2); // prints 3.5 (floating-point)
writeln(7 / 2.0); // prints 3.5 (floating-point)
int a = 7, b = 2;
writeln(a / b); // prints 3
writeln(cast(double)a / b); // prints 3.5
}
double using cast(double).
if StatementExecute code conditionally based on a boolean expression:
import std.stdio;
import std.string;
import std.conv;
void main() {
write("Enter your score (0-100): ");
int score = to!int(readln().strip());
if (score >= 90) {
writeln("Grade: A");
} else if (score >= 80) {
writeln("Grade: B");
} else if (score >= 70) {
writeln("Grade: C");
} else if (score >= 60) {
writeln("Grade: D");
} else {
writeln("Grade: F");
}
}
| Operator | Meaning | Example |
|---|---|---|
== |
Equal to | x == 5 |
!= |
Not equal to | x != 5 |
< |
Less than | x < 5 |
> |
Greater than | x > 5 |
<= |
Less than or equal to | x <= 5 |
>= |
Greater than or equal to | x >= 5 |
| Operator | Meaning | Example |
|---|---|---|
&& |
Logical AND | x > 0 && x < 100 |
|| |
Logical OR | x < 0 || x > 100 |
! |
Logical NOT | !found |
import std.stdio;
import std.string;
import std.conv;
void main() {
write("Enter your age: ");
int age = to!int(readln().strip());
write("Do you have a license? (yes/no): ");
string response = readln().strip();
bool hasLicense = (response == "yes");
if (age >= 16 && hasLicense) {
writeln("You can drive.");
} else if (age >= 16 && !hasLicense) {
writeln("You're old enough but need a license.");
} else {
writeln("You're too young to drive.");
}
}
switch StatementUse switch when comparing a single value against multiple options:
import std.stdio;
import std.string;
import std.conv;
void main() {
write("Enter a day number (1-7): ");
int day = to!int(readln().strip());
switch (day) {
case 1:
writeln("Monday");
break;
case 2:
writeln("Tuesday");
break;
case 3:
writeln("Wednesday");
break;
case 4:
writeln("Thursday");
break;
case 5:
writeln("Friday");
break;
case 6, 7: // D allows multiple case values!
writeln("Weekend!");
break;
default:
writeln("Invalid day number");
}
}
case 6, 7:
while LoopRepeats a block of code as long as a condition is true. The condition is checked before each iteration:
import std.stdio;
void main() {
// Count from 1 to 5
int i = 1;
while (i <= 5) {
writeln("Count: ", i);
i++;
}
}
do-while LoopSimilar to while, but the condition is checked after each iteration. The loop body always executes at least once:
import std.stdio;
import std.string;
import std.conv;
void main() {
int guess;
int secretNumber = 7;
do {
write("Guess a number (1-10): ");
guess = to!int(readln().strip());
if (guess < secretNumber) {
writeln("Too low!");
} else if (guess > secretNumber) {
writeln("Too high!");
}
} while (guess != secretNumber);
writeln("Correct!");
}
for LoopBest for counting a specific number of iterations:
import std.stdio;
void main() {
// Basic counting
for (int i = 1; i <= 5; i++) {
writeln("Iteration ", i);
}
// Counting down
writeln("\nCountdown:");
for (int i = 10; i >= 0; i--) {
writeln(i);
}
// Step by 2
writeln("\nEven numbers:");
for (int i = 2; i <= 10; i += 2) {
writeln(i);
}
}
import std.stdio;
void main() {
writeln("Multiplication Table (1-5):\n");
// Print header row
write(" ");
for (int col = 1; col <= 5; col++) {
writef("%4d", col);
}
writeln("\n --------------------");
// Print table rows
for (int row = 1; row <= 5; row++) {
writef("%2d |", row);
for (int col = 1; col <= 5; col++) {
writef("%4d", row * col);
}
writeln();
}
}
break and continueimport std.stdio;
void main() {
// break - exit the loop early
writeln("Finding first multiple of 7:");
for (int i = 1; i <= 100; i++) {
if (i % 7 == 0) {
writeln("Found: ", i);
break; // exit loop immediately
}
}
// continue - skip to next iteration
writeln("\nNumbers 1-10, skipping multiples of 3:");
for (int i = 1; i <= 10; i++) {
if (i % 3 == 0) {
continue; // skip this iteration
}
writeln(i);
}
}
This program demonstrates input, output, control structures, and loops working together:
import std.stdio;
import std.string;
import std.conv;
void main() {
writeln("=== Temperature Converter ===");
writeln("1. Celsius to Fahrenheit");
writeln("2. Fahrenheit to Celsius");
writeln("3. Quit");
bool running = true;
while (running) {
write("\nEnter choice (1-3): ");
int choice = to!int(readln().strip());
switch (choice) {
case 1:
write("Enter temperature in Celsius: ");
double celsius = to!double(readln().strip());
double fahrenheit = (celsius * 9.0 / 5.0) + 32.0;
writefln("%.2f°C = %.2f°F", celsius, fahrenheit);
break;
case 2:
write("Enter temperature in Fahrenheit: ");
double f = to!double(readln().strip());
double c = (f - 32.0) * 5.0 / 9.0;
writefln("%.2f°F = %.2f°C", f, c);
break;
case 3:
writeln("Goodbye!");
running = false;
break;
default:
writeln("Invalid choice. Please enter 1, 2, or 3.");
}
}
}
| Task | D Syntax |
|---|---|
| Print with newline | writeln("text", variable); |
| Print without newline | write("text"); |
| Formatted print | writefln("Value: %d", x); |
| Read string | string s = readln().strip(); |
| Read integer | int n = to!int(readln().strip()); |
| Read double | double d = to!double(readln().strip()); |
| Compile | gdc filename.d -o outputname |
| Run | ./outputname |
Write a D program that analyzes prime numbers. Your program should:
n (must be ≥ 2)n is prime: A prime number is only divisible by 1 and itselfn is prime: Display "n is a prime number!"n is not prime: Display "n is not prime. Its smallest factor is f." (where f is the smallest factor other than 1)nn-1 divides it evenly (remainder is 0)n, but this is not requiredstd.string for strip() and std.conv for type conversionsSave your program as prime_analyzer.d and compile with:
gdc prime_analyzer.d -o prime_analyzer
./prime_analyzer