CSE3009: 소프트웨어 구조및설계 (Software Architecture and Design) Yann-Gaël Guéhéneuc Testing Method Sequences Slides by Giuliano Antoniol Département de génie informatique et de génie logiciel
Example I � Coin box of a vending machine in C++ – The coin box has a simple functionality and the code to control the physical device is omitted – It accepts only quarters and allows vending when two quarters are received – It keeps track of the total of quarters received (totalQrts) , the current quarters received (curQrts), and whether vending is enabled (allowVend) 2/71
Example I � Coin box of a vending machine in C++ – Methods: adding a quarter, returning current quarters, resetting the coin box to its initial state, and vending and vending 3/71
Example I class CCoinBox { void CCoinBox::AddQtr() { unsigned totalQtrs; curQtrs = curQtrs + 1; unsigned curQtrs; if (curQtrs > 1) unsigned allowVend; allowVend = 1; } public: Ccoinbox() {Reset();} void CCoinBox::Vend() { void AddQtrs(); if (isAllowedVend()) { void ReturnQtrs() { void ReturnQtrs() { totalQtrs = totalQtrs + 2; totalQtrs = totalQtrs + 2; curQtrs = 0; curQtrs = curQtrs - 2; } if (curQtrs < 2) unsigned isAllowedVend() { allowVend = 0; return allowVend; } } } void Reset() { totalQtrs = 0; allowVend = 0; curQtrs = 0; } void Vend(); }; 4/71
UML Statechart Transitions � State transitions caused by events, enabled by guard conditions start [transmission= neutral] Engine Off Engine Off Engine On Engine On have the following general form (all elements are optional) } event(arguments) trigger event name [condition] event dispatch ^target.sendEvent(arguments) guard /method(arguments) executed method 5/71
UML Statechart Transitions Functioning Vend() ReturnQtr() Vend() CCoinBox() Reset() AddQtr allowVend = 0 curQrts = 0 allowVend = 0 curQrts = 1 Vend() AddQtr() Vend() Vend() [self.curQrts = 2] [self.curQrts = 3] ReturnQtr() allowVend = 1 curQrts = 0 allowVend = 1 curQrts:[2,M] ReturnQtr() Vend() [self.curQrts >= 4] Statechart of the code, not fully specified � One corrupt state missing: allowVend=1 curQrts=1 � Transitions missing on states � allowVend=1 curQrts=0 : AddQrts() – allowVend=0 curQrts=0 : ReturnQrt() – allowVend=1 curQrts:[2,M] : AddQrt() – 6/71
Example I � The state diagram indicates that the scenario – AddQtrs() – AddQtrs() – ReturnQtrs() – Vend() is possible! ⇒ Free drinks! ☺ 7/71
Example I � This is a state-dependent fault – Executing some methods is impossible in certain states where they are legal – Some methods sequences that are theoretically not possible can be executed 8/71
Example I � Method structural testing would conclude that, e.g., each edge has been executed � The omission may remain unforeseen even with functional testing Problem: a failure results from a certain sequence of methods Solution: identify minimal set of sequences of methods 9/71
Testing Method Sequences � Motivations � Data Slices – MaDUM – MaDUM – MaDUM for Derived Classes � Method Per- / Post-conditions � Conclusion 10/71
Testing Method Sequences � Motivations � Data Slices – MaDUM – MaDUM – MaDUM for Derived Classes � Method Per- / Post-conditions � Conclusion 11/71
Motivations � Using inheritance context coverage, control- and data-flow techniques can be used to test methods � What about classes? 12/71
Motivations � Testing a class aims at finding the sequence of methods for which a class will be in a state that is contradictory to its invariant or to its methods outputs 13/71
Motivations � Testing classes for all possible sequences of methods is not usually possible – 10 methods ⇒ 10! sequences – If each test requires 1s., we need 1,000 hours 14/71
Motivations � The resources required to test a class increase exponentially with the number of its methods � It is necessary to devise a way to reduce the number of sequences and still provide sufficient confidence 15/71
Motivations � Deriving method sequences – Data slices – Statecharts – Methods pre- / post-conditions – Formal specification, e.g., algebraic specification 16/71
Testing Method Sequences � Motivations � Data Slices – MaDUM – MaDUM – MaDUM for Derived Classes � Method Per- / Post-conditions � Conclusion 17/71
Data Slices � Goal: identify a minimal number of method sequences to test � The state of an object at a single point in time is equivalent to the aggregated state of each of its data members at that point 18/71
Data Slices � The correctness of a class depends on – Whether the instance variables are correctly representing the intended state of an object – Whether the methods are correctly manipulating the representation of the object 19/71
Data Slices � A class is a composition of slices – A slice is a quantum of a class with only a single instance variable and a set of methods, such that each methods manipulate the values that each methods manipulate the values associated with this variable 20/71
Data Slices � Bashir and Goel’s class testing strategy is to test one slice at a time – For each slice, test possible sequences of the methods belonging to that slice • Equivalent to testing a specific instance variable, i.e., the class partial correctness – Repeat for all slices to demonstrate class correctness 21/71
Data Slices � A class K encapsulates a set of variables and provides a set of methods – K = <D(K), M(K)> – D(K) = {d i | d i @ K} – M(K) = {m i | m i @ K} (where @ denotes the relationship between a class and its elements, i.e., “is in”, “belongs to”) 22/71
Data Slices � A data slice of K – Slice di (K) = <d i , M di (K)> • d i ∈ D(K) • M di (K) = {m i | m i @@ d i } (where @@ denotes the usage relationship) (and → denotes a modification) 23/71
Data Slices � Potential problems with data slices – If the code is faulty and a methods that should access a variable does not • The Sequences of methods that interact through that variable would not be tested and the fault may remain undetected – How to identify legal sequences of methods? • There may be a large, possibly infinite, number of legal sequences because a method may be used more than once in a sequence ! 24/71
Testing Method Sequences � Motivations � Data Slices – MaDUM – MaDUM – MaDUM for Derived Classes � Method Per- / Post-conditions � Conclusion 25/71
class SampleStatistic { Example II friend TestSS; // test driver! protected: int n; double x; double x2; double minValue, maxValue; public: sampleStatistic(); virtual ~SampleStatistic(); virtual void reset(); virtual void reset(); virtual void operator +=(double); int samples(); double mean(); double stdDev(); double var(); double min(); double max(); double confidence(int p_percentage); double confidence(double p_value); void error(cont char * msg); }; Formerly part of the GNU C++ library 26/71
double SampleStatistics::stdDev() { if (n <= 0 || this->var() <= 0) return (0); Example II else return (double) sqrt(var()); } double SampleStatistics::var() { if (n > 1) return ((x2 - ((x * x) / 2)) / n - 1); } SampleStatistic::mean() { if (n > 0) if (n > 0) return (x / n); else return (0.0); } SampleStatistic::operator+=(double value) { n += 1; x += value; x2 += (value * value); if (minValue > value) minValue = value; if (maxValue < value) maxValue = value; } 27/71
Generate MaDUM � MaDUM: Minimal Data member Usage Matrix, n × m matrix – n is the number of instance variables – m is the number of methods � MaDUM reports the usage of instance variables by methods – Different usages: reads, reports, transforms 28/71
Generate MaDUM � MaDUM accounts for indirect use of instance variable, through intermediate methods � Use the MaDUM to devise a testing strategy, i.e., a testing order 29/71
Method Categories � Categories: constructors, reporters, transformers, and others � M di (K) = {R di , C, T di , O di } – R – R di = {r di | r di is a reporter method for = {r | r is a reporter method for variable d i } – C = {c i | c i is a constructor of K} – T di = {m di | m di ∉ R di ∧ m di ∉ C ∧ m di → di} – O di = {o di | o di @@ d i ∧ o di ∉ R di ∧ o di ∉ C ∧ o di ∉ T di } 30/71
Method Categories � Categories: constructors, reporters, transformers, and others – Account for indirect use of data members, through intermediate methods intermediate methods – Others • printError() • destructors • … 31/71
Example II � MaDUM accounts for indirect uses – stdDev() does not directly access x and x2 , but calls var() , which does – All SampleStatistic() does is call reset() 32/71
Test Procedure � The method categories is used to decide the testing procedure – Test reporters – Test constructors – Test transformers – Test others � We would like to automate that procedure as much as possible 33/71
Recommend
More recommend