Learn Solidity lesson 23. Loops and conditionals.

João Paulo Morais
Coinmonks
Published in
5 min readAug 13, 2022

--

Solidity has loops and conditionals similar to other programming languages. Its syntax is pretty much the same as C, Java, and JavaScript, so this chapter should be straightforward for anyone who is used to programming in languages like the ones above.

if/else/else if

When the program finds some kind of fork in its flow, where it must follow a certain path if a condition is satisfied, we have a conditional. For this type of situation we use the keywords if/else.

if (condition) {
...
code to be executed if the condition is satisfied.
...
} else {
...
code to be executed if the condition is not satisfied.
...
}

The condition must be an expression that returns true or false, such as x > 3 or (y < 1 && z == 4). Note that Solidity does not convert the value 1 to true and neither convert an empty string to false.

Often, instead of using if/else, it is better to use require to check a condition. They don’t have the same effect and should be used according to the code’s purpose.

Let’s suppose that we want a function to be correctly executed only if the sender of the transaction is an address previously registered in the variable owner. We could have the following.

function onlyOwner() public {
if (msg.sender === owner) {
... some code
}
}

If the sender is not the address of owner, the above function will have no effect, but the transaction will be valid and will not throw an error. This is usually not what we want. We could improve this function to throw an error, as below.

function onlyOwner() public {
if (msg.sender == owner) {
... some code
} else
revert("Sender not owner");
}
}

The transaction will be rolled back if the owner is not the sender of the transaction, via the revert method. The above conditional is common in other programming languages, but in Solidity it is better to use the require method in such cases.

function onlyOwner() public {
require(msg.sender == owner, "Sender not owner");
... some code
}

If the condition inside require is false, the transaction will roll back. As a second parameter, we can send an error message to the sender of the transaction.

Solidity also accepts the else if expression, which allows you to chain conditionals, as below.

if (condition) {... code ...}
else if (condition) {... code ...}
...
else {... code ...}

In other programming languages, the above chained conditional can be replaced by using switch, but this keyword does not exist in Solidity. In the above scenario, we must use multiple if’s.

while, do while and for loops

When we want a block of code to run multiple times, we use some form of loop. Let’s start by looking at the use of while, which executes a block of code while a certain condition is true.

while (condition) {
// code to be executed
}

Inside a loop we can use two keywords: break and continue. If the EVM encounters a break inside a loop, it will exit the loop and continue the flow of code after the loop. If it finds a continue it will skip the rest of the code block and go back to the conditional, for one more iteration of the loop. Let’s see examples.

uint8 last;
uint8 i;
while(i < 10) {
last = i;
i++;
if (i==5) break;
} // last => 4

First we define a variable i that will act as a counter. The variable last will store the last value of the counter inside the conditional. For each iteration, we increment the counter.

When the variable i reaches the value of 4, in the loop block it is incremented to 5 (through the expression i++, which is equivalent to i=i+1). The conditional (i==5) will then be true, break will be executed and the loop is terminated.

An example using the continue keyword is shown below.

uint8 total;
uint8 i;
while(i < 10) {
i++;
if (i==5) continue;
total++;
} // total => 9

The above loop will be executed 10 times, as the variable i will run from 0 to 9. However, the variable total will end up with a value of 9, not 10. This happens because when i is 5, the condition (i==5) will be true and continue will be executed. This way the loop will go back to the beginning and the increment of the variable total will not be executed for that particular iteration.

The do while loop is similar to the while loop, the difference is that the condition is checked after the code block is executed, not at the beginning.

In the example below, at least the first iteration is executed, even though the condition is explicitly false.

uint8 value;
do {
value = 10;
} while(false); // value => 10

In the examples above, three essential ingredients were needed: a counter, a conditional, and a way to increment the counter. These three ingredients are easily implemented using the for loop.

for (initialize the counter; conditional; increment) {
// code to be executed
}

Let’s write an example to iterate over an array and change all of its entries.

uint[] memory array = new uint[](5);for(uint i=0; i < array.length; i++) {
array[i] = i;
} // array => [0,1,2,3,4]

You have to be a little careful when using loops in Solidity, especially for adding/changing state variables. Managing state variables is one of the most gas-intensive operations on Ethereum, so a loop that makes multiple changes to state variables can consume a lot of gas.

Thanks for reading!

Comments and suggestions about this article are welcome.

Any contribution is welcome. www.buymeacoffee.com/jpmorais

Join Coinmonks Telegram Channel and Youtube Channel learn about crypto trading and investing

Also, Read

--

--

João Paulo Morais
Coinmonks

Astrophysicist, full-stack developer, blockchain enthusiast. Technical Writer @RareSkills.