[MUSIC] Along with testing, we have to think about how we measure and the types of things we can measure with tests, types of properties of a system that we can measure with test. And I want to give you a basic understanding of the types of things that we measure. This is not an exhaustive list of the types of things that we can measure, but it can be helpful when we talk about the next topic, which is refactoring. So, when we're talking about tests, we're talking about measuring some property of the system. Usually people equate testing with measuring functional properties of the system. So, these are properties related to how the inputs and the outputs, for example, when we give it the right input, does it produce the right output? So, for example, if we have a function that's adding two numbers together, does providing it two numbers produce the correct output? Does it produce their sum? So that's functional properties. Does it do the correct thing? If we give it the right input, does it produce the correct output and does it do that in all cases? And that's what functional properties are about, is about does it do the right thing? The non-functional properties are also. Important aspects of a system. And these are about how it does what it does. So, for example, you can have the same system that adds two numbers together, and it does it correctly. It always adds the two numbers correctly, but one system may take one millisecond to add the two numbers together. That's actually still a really slow system. And the next system may take two hours to add the numbers together. And they're still both producing the correct output for a given input. But they're producing that output in a vastly different fashion. One is doing it relatively quickly compared to the other one. So, we have one millisecond versus one hour. They're both yielding the same result, but obviously the one that's producing the output much faster is the one that we probably like a lot better. So, performance could be a non-functional property that we care about. And something that we want to measure in a system. We can also have other things. For example, let's say that we are storing data for patients going into a hospital. We can have the same system that allows us to store the patient data, and when we store it, we can retrieve it. It's accurate when we retrieve it, so we're getting the correct functional capability out of the system. But we can have one system that allows anybody anywhere in the world to access it through the Internet and collect patient data that they shouldn't have access to. And another version that very carefully password controls and protects that information. So, one version has a, and let me rephrase this, so they both, let's say, password protect the information. But one of them has a security vulnerability in how it goes about protecting information. So, there could be security concerns that could be non-functional that we want to measure. So, whether or not a system is secure or not is a property that we care about. And if we have two systems that do exactly the same thing, and one does it correctly and the other one also does it correctly, but one is secure and one is insecure, that's another aspect of the system that we probably care about. Just like the speed of doing something versus other things that we care about. Now, another important one that we can think about is, let's say that we build some software, and we've all heard terms like spaghetti code, for example. Or we've heard people talking about software that was poorly designed. We can have software that meets its functional goals but is very poorly written on the inside. And when it's poorly written it may be hard to evolve and maintain overtime. Because going and making a change, it's very hard to figure out where to make the change. And if we make that change, it may require us to change that same thing in lots of different places. So, we have code duplication. When we want to go and make a simple change, it requires us to change lots of other things. We have tight coupling. So, other properties that matter are things like extensibility. Is it easy to add things to the system? We may have reliability, maintainability. All of these other things can be non-functional properties that we measure about a system. So, when you hear the term functional properties, think of, if I give it the right input, does it produce the right output? And nonfunctional properties, does it produce that output in a way that is appropriate? Is it fast enough? Is it secure enough? Is the code itself extensible enough? So it's about how it does it, rather than doing it correctly. Well, although certainly failing non-functional properties can be doing it incorrectly as well. But it produces the right output, given an input. But it may do it too slowly, or do it with some other non-functional property that we want to improve upon.