💃 Calculate the performance of your Apex 🕺

A fundamental tool for devs 🛠️

Good morning, Salesforce Nerds!

Today I thought we’d dive 🤿 into something a little extra fun! 🎡 

We’re check out how the code we’re writing can be mathematically proven to be considered 🔥 or 💩!

We may need to dust off whatever part of our brains 🧠 is holding on to those high school algebra 🏫 memories, but I think we’ll be okay!

I’m not going to try to boil the ocean 🌊 - I’ll keep as high-level and light as I can!

🫣

❤️ 

PARDON THE INTERRUPTION

Survey Season

The ChaCha wants to be your valued resource, and we need your feedback to give you the best content possible.

Can you please take this 2 minute survey 🥹

If you’ve already completed the survey, please disregard and thank you so much ❤️❤️❤️

 💜 

INTRO TO BIG O NOTATION

Big O notation is a mathematical notation that describes the limiting behavior of a function when the argument tends towards a particular value or infinity. Big O is a member of a family of notations invented by German mathematicians Paul Bachmann,[1] Edmund Landau,[2] and others, collectively called Bachmann–Landau notation or asymptotic notation. The letter O was chosen by Bachmann to stand for Ordnung, meaning the order of approximation.

Wikipedia’s definition of Big O notation

I know right? 🤯

Don’t stress, let’s break this down a bit … 🧩 

Think of Big O notation as a way we can analyze the amount of complexity there is within a particular function. 📈 

This is going to help us understand the magnitude (or scale) of said function. ⏳️ 

Some basics to know:

The O stands for Order (order = growth rate of a function)

It follows the convention of writing O and then the complexity (# of operations) in parenthesis - O(1), O(n), O(n2), etc.

 n denotes the size or number of items input into the function

So … we’re measuring the growth rate (O) of a function as it executes relative to the size of its input (n). 😴 

Whatever … I know, math sucks sometimes. 😡 

But, hang in there. Some examples will help. I promise. 👇️ 

KNOW THY COMPLEXITIES

I’m just going to talk about what the three (3) notations I think will intro the topic sufficiently, give y’all an understanding how they work, and why they’re important. 📑 

Then we’ll call it day. 🍻 

There’s a wealth of knowledge out there on this topic if you’re interested in more. ℹ️ 

🚀 O(1)

Known as a constant-time function. ⏲️ 

Order 1 functions are the least complex. 💯 These execute in a constant amount of time regardless of the how big the input size is. 🎯 

Take this example:

public void printSize(List accounts) { System.debug('There are ' + accounts.size() + ' accounts in the list.'); }

☝️ This function is rated O(1) because, given a list of any size, it simply logs the length of the collection.

We can pass in 1 account or 1000 accounts. It won’t matter. The number of operations run will stay the same. It’s a fixed constant. 💪 

🚀 O(n)

AKA a linear-time constant. 📈 

Order N functions add a bit of complexity to things. 😬 They’re super common, though - especially in the world of Salesforce. 🙂 

These execute in differing amounts of time depending on the size of what’s passed in. 📦️ 

What if we wrote a function similar to the one up there ☝️ but with one difference:

public void printNames(List accounts) { for(Account acct :accounts) { System.debug('This account is named: ' + acct.Name); } }

Check what we changed.  

Instead of just a single operation happening on the collection of accounts, now we’re looping over each account and logging the name. ✍️ 

We’re good if we pass 1 account in, but if we pass 1000 … we’ve added 1000 operations. 😰 

🚀 O(n2)

While the AKA sounds awesome - 💥💥 QUADRATIC-TIME FUNCTION 💥💥 - you want to avoid these whenever you can. 🛑 

Sometimes you can’t … so you may need to mitigate. 🔀 

In the case of an Order N2 function, the number of operations performed scales in proportion to the square of the input size. 🤔 

Basically, be wary of nested loops. 🐉 

What happens here is you have a collection of items that you’re iterating over and for each iteration, you need to iterate over the collection again to perform some operation. 😅 

Check this example out 👇️

public boolean checkForDupes(List accounts) { boolean hasDupes = false; for(Account outerAcct :accounts) { for(Account innerAcct :accounts) { // Skip when it's the same record if(outerAcct.Id == innerAcct.Id) { continue; } if(outerAcct.Name == innerAcct.Name) { hasDupes = true; } } } return hasDupes; }

Super basic code, iterating over a list of accounts to see if duplicate names exists or not. 👍️ 

This is the type of thing that can quickly get out of control. 😱 

If you can - avoid this! 🛑 

However, if you can’t, be sure to proactively leave a loop(s) when you’re done with your operation. ⏩️ 

In this case here, we could have simply added a break statement to the innermost loop after finding the duplicate. 🔍️ 

Like so:

if(outerAcct.Name == innerAcct.Name) {
    hasDupes = true;
    break;
}

WHY IS THIS IMPORTANT

They say a picture is worth a thousand words. 🖼️ 

Keep it 🟢 or 🟡 

Still? What’s so important here? 🤔 

The answer is that studying Big O notation makes you grasp the very important concept of efficiency in your code. 📈 

So when you do work with huge data sets, you will have a good sense of where major slowdowns are likely to cause bottlenecks, and where more attention should be paid to get the largest improvements. 📉 

Daily Principle

"The real problem is that programmers have spent far too much time worrying about efficiency in the wrong places and at the wrong times; premature optimization is the root of all evil (or at least most of it) in programming.”

Donald Knuth

and now....Your Daily Memes

We all know he goes … we’ve done it ourselves, too

Let it burn 🔥🔥

Simple line of code can save some ⌚️ 

What did you think about today's newsletter?

Login or Subscribe to participate in polls.