Arduino:
Refactoring

How to:

Let’s say you’ve got a function on your Arduino that’s doing way too much, like this:

void setup() {
  Serial.begin(9600);
}

void loop() {
  // A function that's doing too much
  handleEverything();
}

void handleEverything() {
  // Read sensor data
  int sensorValue = analogRead(A0);
  // Process the sensor data
  sensorValue = map(sensorValue, 0, 1023, 0, 255);
  // Print the sensor data
  Serial.println(sensorValue);
  delay(500);
}

Refactoring it might look like splitting handleEverything() into smaller, more focused functions:

void setup() {
  Serial.begin(9600);
}

void loop() {
  int sensorValue = readSensorData();
  int processedValue = processSensorData(sensorValue);
  printData(processedValue);
  delay(500);
}

int readSensorData() {
  return analogRead(A0);
}

int processSensorData(int sensorValue) {
  return map(sensorValue, 0, 1023, 0, 255);
}

void printData(int data) {
  Serial.println(data);
}

After refactoring, the loop() function is more readable, and each task is handled by a dedicated function, making the code easier to manage.

Deep Dive

Historically, refactoring became popular with the rise of Agile and Test-Driven Development (TDD) methodologies, which rely on constant code improvement to adapt to changing requirements. There are various tools and strategies for refactoring — like the “Extract Method” technique we used in our Arduino example. This is essential when you’re moving from a quick prototype to a stable project, where code readability and maintenance become crucial.

When refactoring, it’s important to have a good set of tests in place to ensure that changes haven’t introduced any bugs. In the Arduino world, automated testing isn’t always straightforward due to hardware dependencies, but you can still use unit testing for pure logic parts or employ simulators.

Alternatives to manual refactoring include using dedicated refactoring tools, which automate the identification of code smells and suggest changes. However, these tools often lack the nuance for microcontroller code and might not be available in the Arduino development environment.

Ultimately, refactoring is an art that balances improving the internal structure of the code against the risk of introducing defects. It requires you to think about implementation details like memory usage and processor time, especially due to the resource-constrained nature of microcontrollers.

See Also

You can dive deeper into refactoring with Martin Fowler’s seminal book Refactoring: Improving the Design of Existing Code. For a closer look at Arduino-specific practices, check out the Arduino development forums and communities:

Remember, the goal is clean, comprehensible code that future you, and others, will thank you for. Keep hacking, and keep it tidy!