0204: Coverage measurement

cs128
14 Sept 202106:01

Summary

TLDRThis lesson delves into test-driven development's coverage measurement, emphasizing the importance of thorough testing beyond just general cases to include edge cases. It introduces different levels of code coverage, from simple method execution (S0) to comprehensive pathway testing (C2), suggesting that while more tests are better, the real question is how thorough the testing is. The instructor highlights the balance between testing enough and over-testing, and the value of various coverage metrics in ensuring software correctness.

Takeaways

  • 🔍 Coverage measurement is a key aspect of test-driven development to ensure the thoroughness of tests.
  • 🛠️ Different levels of coverage provide varying degrees of confidence in the correctness of the code.
  • 🤔 The question 'how much testing is enough?' is addressed by considering the balance between testing and shipping software.
  • 📈 A quantitative evaluation can be made by comparing lines of test code to lines of code in the application.
  • 📊 Having more tests than lines of code is not unreasonable, especially in production-level systems.
  • 🧐 The focus should be on the thoroughness of testing rather than just the quantity of test code.
  • 📋 Basic coverage measurements include S0 (every method is called) and S1 (every method is called from every call site).
  • 🔄 C1 coverage involves executing every branch in both directions to test all possible pathways.
  • 🌐 C2 coverage is about testing every possible combination of pathways through a method, which is challenging and controversial.
  • 🚀 The lecture will continue with more on test-driven development in the next video.

Q & A

  • What is the primary focus of the lesson in this script?

    -The lesson focuses on coverage measurement within the context of test-driven development, exploring different levels of coverage to evaluate how thoroughly code is being tested.

  • What is the basic idea behind code coverage in testing?

    -Code coverage refers to the extent to which tests cover the code base. Higher coverage indicates that more parts of the code, including edge cases and different pathways, have been tested, which increases confidence in the correctness of the code.

  • Why is it not ideal to keep testing until the software is ready for release?

    -Continuously testing until release may indicate a lack of methodical planning in the testing process, leading to ineffective or redundant testing. It's better to structure tests in a methodical manner for optimal coverage.

  • Why might measuring the number of test cases against lines of code be insufficient?

    -Simply having more tests than lines of code does not necessarily indicate thoroughness, as the tests could be poorly written or fail to cover critical parts of the code. It's more important to consider the quality and scope of the tests.

  • What is S0 coverage in testing?

    -S0 coverage indicates that every method in the code has been called at least once, though it doesn't guarantee that all possible code paths have been exercised or that edge cases are covered.

  • How does S1 coverage improve upon S0 coverage?

    -S1 coverage ensures that every method is called from every possible call site, allowing for a more comprehensive evaluation of the function's behavior in different contexts, though it may still neglect fringe or edge cases.

  • What does C1 coverage ensure in unit testing?

    -C1 coverage ensures that every statement in a method is executed at least once, including both branches of conditional statements. This provides a more thorough test than just calling the method or function.

  • What does C2 coverage aim to achieve in testing?

    -C2 coverage aims to test every possible combination of paths through the code, requiring a large number of test inputs to ensure that every potential pathway is covered. However, it is complex and sometimes debated in terms of its value.

  • Why is C2 coverage considered difficult to achieve?

    -C2 coverage is difficult because it requires testing every possible pathway through a function, which often involves a huge number of test cases. This makes it complex and resource-intensive, and there is debate about how valuable it is in practice.

  • What is the overall purpose of measuring coverage in test-driven development?

    -The purpose of measuring coverage is to ensure that tests thoroughly exercise the code, increasing confidence in its correctness and stability. Higher coverage, especially when it includes edge cases and different pathways, leads to better software reliability.

Outlines

00:00

📏 Coverage Measurement in Test-Driven Development

This paragraph introduces the concept of coverage measurement in the context of test-driven development. It explains that tests can vary in their level of coverage, from general cases to edge cases. The importance of thorough testing is emphasized to ensure that the code is exercised to its fullest potential, leading to more confidence in the correctness of the code. The discussion also touches on the question of how much testing is enough, suggesting that having more tests than lines of code is not unreasonable, especially in production-level systems where failure implications are significant. The paragraph outlines different levels of coverage, starting from S0, which is simply calling every method, to S1, which involves calling every method from every call site. It also introduces the idea of executing every statement within a function and considering both directions of every branch (C1 coverage), setting the stage for a deeper discussion on test coverage in subsequent lessons.

05:01

🔍 Advanced Coverage Measurement and Its Value

This paragraph delves into more advanced forms of coverage measurement, such as considering every possible combination of pathways through a method or function. It discusses the challenge of creating test cases that can execute every path, which often requires a multitude of inputs to direct the code down different pathways. The paragraph also introduces the concept of C2 coverage, which is very difficult to achieve and is a subject of debate within the software engineering community regarding its value. The speaker acknowledges the complexity of achieving comprehensive test coverage and suggests that the next video will continue the discussion on test-driven development, implying a progression towards more practical applications of these concepts.

Mindmap

Keywords

💡Test Driven Development (TDD)

Test Driven Development (TDD) is a software development approach where tests are written before the actual code. This ensures that the code is designed to be testable and allows developers to catch errors early in the development process. In the video, TDD is the overarching theme, with coverage measurement being a key aspect of this methodology.

💡Coverage Measurement

Coverage measurement refers to assessing how thoroughly the source code is tested by a given set of tests. It is a metric used to determine the effectiveness of testing in a software development process. The video emphasizes the importance of coverage measurement as a way to gauge the confidence in the correctness of the code.

💡General Case

The general case is a scenario in testing where the most common or expected inputs and conditions are considered. The video mentions that some tests might only cover the general case, ignoring edge cases, which could lead to incomplete testing and potential undiscovered bugs.

💡Edge Cases

Edge cases are scenarios that test the boundaries of the input range or unusual conditions. They are critical for uncovering bugs that may not appear under normal circumstances. The script discusses the importance of considering edge cases in testing to ensure robustness of the software.

💡Confidence

In the context of the video, confidence refers to the assurance that the software functions correctly as intended. Higher levels of test coverage contribute to greater confidence in the software's reliability and correctness.

💡Lines of Test/Code Ratio

This ratio compares the amount of test code to the amount of production code written. The video suggests that having more lines of test code than production code is not unreasonable, especially in production-level systems where failure could have significant consequences.

💡Thoroughness

Thoroughness in testing refers to the extent to which all possible scenarios are considered and tested. The video posits that thorough testing is more valuable than simply having a large quantity of tests, as it ensures comprehensive coverage of all potential code paths.

💡S0 Coverage

S0 Coverage is a basic level of testing where every method in the application is called at least once. The video uses S0 as an example of a minimal testing approach, suggesting that while it's a start, it does not provide deep insights into the functionality of the code.

💡S1 Coverage

S1 Coverage involves calling every method from every possible call site. This is a more comprehensive approach than S0, as it tests how methods behave when called from different contexts within the application, providing a better understanding of their functionality.

💡C1 Coverage

C1 Coverage is a testing level where every statement and every branch (like if-else conditions) are executed. This ensures that all code paths are tested, including both the true and false outcomes of conditional statements.

💡C2 Coverage

C2 Coverage aims to test every possible combination of code paths within a method. This is a very high level of testing that is challenging to achieve and is debated in the software engineering community for its practical value. The video mentions this as the most difficult type of coverage to achieve.

Highlights

Introduction to coverage measurement as part of test-driven development.

Explanation of different levels of test coverage, such as testing general cases versus edge cases.

Importance of exercising all pathways in code to ensure comprehensive testing.

Mention of Armando Fox and David Patterson's textbook as a reference for software testing concepts.

The idea that simply testing until software is ready to ship is not a methodical approach.

Quantitative evaluation: ratio of lines of test code to lines of application code.

Clarification that having more tests than lines of code is common in production-level systems.

Discussion of the limitations of just having a lot of test code, emphasizing thoroughness over quantity.

Introduction of different coverage measurements, including S0, S1, and C1.

S0 coverage ensures that every method in the application is called.

S1 coverage: calling every method from every call site, providing better insight than S0.

C1 coverage ensures every statement and every branch is tested, improving test accuracy.

C2 coverage: the most complex, requiring tests that cover every possible pathway through the code.

Challenges with C2 coverage, as it requires many inputs and may not always be practical.

The next step in the lesson is to continue with test-driven development practices.

Transcripts

play00:00

Howdy, and welcome back.

play00:02

So the next topic, uh, within this short lesson on test

play00:06

driven development is going to be coverage measurement.

play00:09

If we think about kind of crafting, uh, tests, and you

play00:13

could think about doing this by hand, there's different

play00:16

levels of coverage that those tests may come up with.

play00:20

You might come up with tests that only exercise,

play00:23

say the general case and completely disregard

play00:26

fringe cases or edge cases.

play00:28

This would be essentially testing the method once

play00:31

and not considering all of the pathways through it.

play00:34

Uh, what we'll see here is that with different level

play00:37

of coverage comes to us, um, essentially more confidence

play00:43

that, uh, the tests are indeed exercising the code to the

play00:47

fullest ability of their potential, and that the results

play00:49

are going to be rather, um, informative to us and will be-,

play00:53

have that much, uh, stronger confidence in that the code

play00:55

that we've written is correct.

play00:59

So how much testing is enough might be our first question.

play01:03

Uh, this is again from Armando Fox, and I believe

play01:07

it's David Patterson's, uh, textbook, uh, kind of slide

play01:11

I stole for my software engineering lecture slide.

play01:14

So how much testing is enough?

play01:15

Well, it's bad if we keep testing until we are ready

play01:19

to ship the software.

play01:21

That means we're, y'know, obviously going, not

play01:23

going about the testing in a methodical manner.

play01:26

It could be that we're writing our test cases towards the

play01:30

end, so just continuously and mindlessly perhaps testing

play01:35

until we're ready to release, uh, that that's probably not

play01:38

the best way to go about this.

play01:40

So one k-, more quantitative perhaps, um, evaluation of

play01:44

this might be to take the lines of test and divide

play01:46

it by the lines of code written in your application.

play01:50

Um, having more tests than lines of code is

play01:52

not, um, unreasonable.

play01:55

It frequently happens.

play01:56

Uh, though this occurs much more frequently in production

play02:00

level systems specifically.

play02:02

Uhm, y'know, those where if it does fail, the

play02:05

implications are huge.

play02:07

So a better question perhaps to ask than, y'know, coming

play02:10

up with these metrics that are fractions and not

play02:14

necessarily as informative.

play02:15

Because if you just have a bunch of test code, it doesn't really

play02:19

communicate how thorough it is.

play02:20

It could all be garbage.

play02:22

So the better question, here's going to be, how

play02:24

thorough is my testing?

play02:25

We'll see here that there's a number of different

play02:27

cover measurements, uh, to help us describe.

play02:32

So the basics, I'm going to just focus on these, uh, five.

play02:37

I'm going to briefly comment on, uh, what they are and

play02:40

we'll kind of leave it at that.

play02:42

This is an introductory course.

play02:43

It's not a software engineering course.

play02:45

I'm not expecting to get too into this, but I would

play02:48

like to draw your attention that there are different

play02:51

coverages, um, that we can write our unit test to.

play02:55

Obviously, uh, y'know, the more coverage, the better.

play03:00

S0 is going to be essentially communicating that

play03:03

every method within our application has been called.

play03:06

And this is simply just calling it, uh, we're not necessarily,

play03:10

um, calling it from every location within our application.

play03:14

It's simply just being called and we're evaluating.

play03:17

Um, whether or not that call succeeds in perhaps against

play03:21

some basic test suite.

play03:23

So notice here if we're just kind of testing it

play03:25

independently, that's not too informative.

play03:27

How did we, how did we get to that point, um, could,

play03:31

y'know, have impact in terms of the actual errors?

play03:33

So, uh, S1's a little bit better.

play03:36

It's calling every method from every call site.

play03:39

So every area where, uh, of that particular call is made

play03:44

to a function, we go ahead and execute that line of code.

play03:47

That can provide a, uh, more, a-a better understanding perhaps

play03:52

as to, uh, whether or not we've successfully implemented, um,

play03:57

that function because it's being called from multiple ver

play04:00

multiple different context.

play04:03

So if that seems to work, and that could be just kind

play04:05

of looking at the general cases and maybe we're,

play04:09

y'know at this point, uh, neglecting the fringe cases.

play04:12

So, what can, what we're kind of interested in then

play04:15

is then looking at the actual composition of the, uh, of the

play04:20

function itself and writing unit tests that execute

play04:24

every statement within, say that particular function.

play04:29

We could take this a step further, and we can execute

play04:32

every branch in both directions.

play04:35

So coming up with very, uh, involved test suites

play04:38

that essentially has input combinations that exercise not

play04:43

only every statement presenting within, say a particular

play04:46

method, like if x, do would-, could be executing that if

play04:50

statement a single time.

play04:52

The C1 coverage says we're going to execute every statement

play04:55

and for every branch we're going to consider, we're

play04:58

going to have code that's going to run us through both

play05:00

the if and the else pathway.

play05:03

Now we can take this to an even, uh, bigger stream is looking at.

play05:07

Every combination of every pathway through a particular

play05:10

method or function.

play05:11

And exerci coming up with test cases that exercise, um, that,

play05:16

and again, these aren't, it's not like a single test case

play05:18

is going to be able to hit every path in you our code.

play05:22

We're going to need to come up with a multiple, u-uh y'know

play05:25

a huge number of inputs in this case so that we could

play05:28

execute, uh, every path with each input, perhaps directing

play05:32

us down one pathway that another took a different routing.

play05:37

This last coverage C2 is very difficult and there is some

play05:41

disagreement in the software engineering community, how

play05:43

valuable it actually is.

play05:47

So we'll go ahead and go forward with our test driven,

play05:50

uh, development, uh, section of this lesson in the next video.

play05:55

function.

play05:56

And exerci-, coming up with test cases that exercise, um,

play06:00

that, and again, these aren't, it's not like a single test

play06:02

case is going to be able to hit every path in you our code.

play06:06

We're going to need to come up with a multiple, u-uh y'know

play06:09

a huge number of inputs in this case so that we could

play06:13

execute, uh, every path with each input, perhaps directing

play06:17

us down one pathway that another took a different routing.

play06:21

This last coverage C2 is very difficult and there is some

play06:25

disagreement in the software engineering community, how

play06:27

valuable it actually is.

play06:32

So we'll go ahead and go forward with our test driven,

play06:35

uh, development, uh, section of this lesson in the next video.

play06:39

path in you-, our code.

play06:41

We're going to need to come up with a multiple, u-uh y'know

play06:44

a huge number of inputs in this case so that we could

play06:47

execute, uh, every path with each input, perhaps directing

play06:52

us down one pathway that another took a different routing.

play06:56

This last coverage C2 is very difficult and there is some

play07:00

disagreement in the software engineering community, how

play07:02

valuable it actually is.

play07:07

So we'll go ahead and go forward with our test driven,

play07:09

uh, development, uh, section of this lesson in the next video.

play07:14

multiple, u-uh, y'know a huge number of inputs in this case

play07:18

so that we could execute, uh, every path with each

play07:22

input, perhaps directing us down one pathway that another

play07:26

took a different routing.

play07:28

This last coverage C2 is very difficult and there is some

play07:32

disagreement in the software engineering community, how

play07:34

valuable it actually is.

play07:38

So we'll go ahead and go forward with our test driven,

play07:41

uh, development, uh, section of this lesson in the next video.

play07:46

next video.

Rate This

5.0 / 5 (0 votes)

Ähnliche Tags
Test-Driven DevelopmentCoverage MeasurementSoftware EngineeringCode TestingDevelopment Best PracticesQuality AssuranceEdge CasesMethodical TestingCode ConfidenceTesting Metrics
Benötigen Sie eine Zusammenfassung auf Englisch?