Skip to main content

Lesson 1: C++ Basics

This lesson covers fundamental C++ concepts you need to read and write FRC robot code. We'll focus on the essentials: variables, functions, classes, references, and how C++ programs are organized with headers and includes.

Who This Is For​

If you're new to programming or coming from another language, this lesson provides a practical foundation. The goal is to help you understand existing FRC code (like state machines, command factories, and subsystem patterns) and start making your own contributions.

Variables and Types​

Variables store data in your program. In C++, every variable has a type that determines what kind of data it holds and how much memory it uses.

Basic Types​

// Integer types
int robotState = 0; // Whole numbers (-2147483648 to 2147483647)
bool isEnabled = true; // Boolean: true or false
double motorSpeed = 0.5; // Floating-point numbers (decimals)

// Text
std::string teamName = "TEAM1771"; // String of characters

// Auto type deduction (C++11+)
auto currentTime = 2.5; // Compiler figures out it's a double

FRC Context​

In robot code, you'll see types like:

  • int for counters, state indices, button IDs
  • double for motor speeds, sensor readings, timestamps
  • bool for flags like "is the mechanism ready?"
  • std::string for dashboard labels

Key Point: C++ is statically typed—you declare the type upfront, and it doesn't change. This catches errors early.

Further Reading​

Functions​

Functions are reusable blocks of code that perform a specific task. They can accept inputs (parameters) and return outputs.

Basic Function Syntax​

// Function that takes two integers and returns their sum
int add(int a, int b) {
return a + b;
}

// Function with no return value (void)
void printStatus(std::string message) {
std::cout << message << std::endl;
}

// Function with no parameters
double getCurrentTime() {
return 42.0; // Placeholder
}

FRC Context​

In robot code, functions help organize logic:

  • processState() in subsystems handles state machine transitions
  • setDesiredStateCmd() creates commands that request state changes
  • Periodic() runs telemetry callbacks every robot loop

Key Point: Functions let you break down complex robot behavior into manageable, testable pieces.

Further Reading​

Classes​

Classes bundle data (member variables) and functions (methods) together. They're the foundation of object-oriented programming and WPILib's command-based architecture.

Basic Class Example​

class Motor {
private:
double m_speed; // Member variable (m_ prefix is team convention)
bool m_isInverted;

public:
// Constructor: runs when you create a Motor object
Motor() : m_speed(0.0), m_isInverted(false) {}

// Method to set speed
void setSpeed(double speed) {
m_speed = m_isInverted ? -speed : speed;
}

// Method to get speed
double getSpeed() const {
return m_speed;
}
};

// Using the class
Motor leftMotor;
leftMotor.setSpeed(0.5);

FRC Context​

In FRC code, classes represent:

  • Subsystems: ExampleSubsystem, Climber, Intake
  • Commands: RunOnce, Run, custom command classes
  • Utilities: Controllers, state machines, telemetry helpers

Each subsystem is a class with:

  • Private hardware objects (motors, sensors)
  • Public command factories (setDesiredStateCmd(), runSubsystemCmd())
  • State machine logic in processState()

Key Point: Classes encapsulate robot mechanisms, hiding hardware details and exposing high-level control.

Further Reading​

References​

References are aliases to existing variables. They let you access or modify a variable without copying it.

Reference Basics​

int count = 10;
int& ref = count; // ref is a reference to count

ref = 20; // Changes count to 20
std::cout << count; // Prints: 20

Pass by Reference​

// Pass by value (copies the variable)
void incrementCopy(int x) {
x = x + 1; // Only changes local copy
}

// Pass by reference (modifies the original)
void incrementRef(int& x) {
x = x + 1; // Changes the original variable
}

int value = 5;
incrementCopy(value); // value is still 5
incrementRef(value); // value is now 6

Const References​

// Pass by const reference (read-only, no copy)
void printMessage(const std::string& message) {
std::cout << message << std::endl;
// Can't modify message here
}

FRC Context​

References are everywhere in FRC code:

  • Passing large objects efficiently (avoid copying)
  • Returning state snapshots: const StateSnapshot& getState()
  • Lambda captures: [&] captures variables by reference

Key Point: Use references to avoid expensive copies and to modify variables in place.

Further Reading​

Includes and Header Files​

C++ programs are split into header files (.h) and implementation files (.cpp). This separation keeps declarations public and implementation details private.

Header File (.h)​

// Motor.h
#pragma once // Prevents multiple inclusion

class Motor {
private:
double m_speed;

public:
Motor();
void setSpeed(double speed);
double getSpeed() const;
};

Implementation File (.cpp)​

// Motor.cpp
#include "Motor.h"

Motor::Motor() : m_speed(0.0) {}

void Motor::setSpeed(double speed) {
m_speed = speed;
}

double Motor::getSpeed() const {
return m_speed;
}

Using the Class​

// RobotContainer.cpp
#include "subsystems/Motor.h"

Motor myMotor;
myMotor.setSpeed(0.75);

FRC Context​

In robot code:

  • Headers (ExampleSubsystem.h) declare the class interface: public methods, state enums, state snapshots
  • Implementation (ExampleSubsystem.cpp) contains the actual logic: processState(), command factories, telemetry registration
  • Includes bring in WPILib classes: <frc2/command/SubsystemBase.h>, <frc/smartdashboard/SmartDashboard.h>

Key Point: Headers let other files see what a class does without seeing how it does it. This keeps compilation fast and code modular.

Include Guards​

// Old style (still works)
#ifndef MOTOR_H
#define MOTOR_H
// ... class definition ...
#endif

// Modern style (preferred)
#pragma once
// ... class definition ...

FRC Note: TEAM1771 uses #pragma once for simplicity.

Further Reading​

Reading FRC Code​

Now that you know the basics, you can understand patterns in FRC robot code:

State Machine Pattern​

// In ExampleSubsystem.h
enum class STATE { OFF, ON, IDLE };

// In ExampleSubsystem.cpp
void ExampleSubsystem::processState() {
switch (m_desiredState) {
case STATE::OFF:
handleOffState();
break;
case STATE::ON:
handleOnState();
break;
case STATE::IDLE:
handleIdleState();
break;
}
}

What's happening?

  • enum class STATE declares possible states (variables with a custom type)
  • processState() is a function that checks the current state
  • switch statement routes to the right function for each state
  • Each handle*State() function contains the logic for that state

Command Factories​

frc2::CommandPtr ExampleSubsystem::setDesiredStateCmd(STATE state) {
return frc2::cmd::RunOnce([this, state]() { m_desiredState = state; }, {this});
}

What's happening?

  • This function returns a command (reusable block of robot logic)
  • RunOnce runs a lambda function exactly once
  • [this, state] captures the subsystem and state by value
  • The lambda sets m_desiredState (member variable reference)

Hold-to-Run Bindings​

m_controller.R2().WhileTrue(m_exampleSubsystem.setDesiredStateCmd(STATE::ON))
.OnFalse(m_exampleSubsystem.setDesiredStateCmd(STATE::OFF));

What's happening?

  • R2() gets a reference to the R2 button
  • WhileTrue() runs a command while the button is held
  • OnFalse() runs a command when the button is released
  • Commands call functions that change subsystem state variables

Going Deeper​

This lesson covers the essentials, but C++ has much more to explore. When you're ready for more depth:

TEAM1771 Crash Course Wiki​

The TEAM1771 Crash Course is a comprehensive resource that covers:

  • Common C++ features (loops, conditionals, arrays, vectors)
  • Advanced topics (smart pointers, templates, lambdas)
  • FRC-specific libraries (WPILib, Phoenix, REVLib)
  • Best practices for robot code

When to use it: If you see unfamiliar syntax in robot code or want to understand a specific feature in detail.

The Cherno's C++ Playlist​

The Cherno's C++ series is a high-quality video course covering C++ from beginner to advanced.

Recommended videos (in addition to those linked above):

Tip: You can skip videos about Visual Studio setup—we use VS Code with WPILib extensions instead.

Practice Project​

Ready to write some C++? Check out the 01-cpp-basics project in the projects/ folder of the Bootcamp repository to practice these concepts with a hands-on interactive exercise.

The project involves:

  • Creating a simple class
  • Reading user input from the command line
  • Processing data with functions
  • Printing results

No WPILib required—run it in any C++ editor or locally with g++.

Next Steps​

After completing this lesson and the practice project:

  1. ✅ Review code in projects/00-setup-check/ with your new C++ knowledge
  2. 📖 Study the Style Guide to see how these concepts apply to team patterns
  3. 🚀 Move to the next lesson to learn more about WPILib command-based programming

Additional Resources​