9
FEN 2013-04-07 UCN T&B - PBA/CodeContract-Intro 1 Code Contract Introduction Specification of a Person Class

FEN 2013-04-07UCN T&B - PBA/CodeContract- Intro 1 Code Contract Introduction Specification of a Person Class

Embed Size (px)

Citation preview

Page 1: FEN 2013-04-07UCN T&B - PBA/CodeContract- Intro 1 Code Contract Introduction Specification of a Person Class

FEN 2013-04-07 UCN T&B - PBA/CodeContract-Intro

1

Code Contract Introduction

Specification

of a

Person Class

Page 2: FEN 2013-04-07UCN T&B - PBA/CodeContract- Intro 1 Code Contract Introduction Specification of a Person Class

Installation

• Download from this URL:

http://msdn.microsoft.com/en-us/devlabs/dd491992.aspx

FEN 2013-04-07 UCN T&B - PBA/CodeContract-Intro 2

• Choose ‘Premium Edition’

• Download the documentation

• Install the plug-in and open Visual Studio

Page 3: FEN 2013-04-07UCN T&B - PBA/CodeContract- Intro 1 Code Contract Introduction Specification of a Person Class

Visual Studio

• Use this namespace• Add a reference (right-

click on the project) to Microsoft.Contracts

FEN 2013-04-07 UCN T&B - PBA/CodeContract-Intro 3

Page 4: FEN 2013-04-07UCN T&B - PBA/CodeContract- Intro 1 Code Contract Introduction Specification of a Person Class

Right-click on the project and choose ‘Properties’, then choose ‘ Code Contracts’

FEN 2013-04-07 UCN T&B - PBA/CodeContract-Intro 4

Page 5: FEN 2013-04-07UCN T&B - PBA/CodeContract- Intro 1 Code Contract Introduction Specification of a Person Class

FEN 2013-04-07 UCN T&B - PBA/CodeContract-Intro 5

class Person{

private String name;private int weight;public int Weight { get; private set; }[ContractInvariantMethod] private void ObjectInvariant()

{ Contract.Invariant(!name.Equals("")

&& weight >= 0);}[Pure]public override String ToString(){

Contract.Ensures(Contract.Result <string>()

!= null);return "Person(\"" + name

+ "\"," + weight + ")"; }

[Pure]public int GetWeight()

{

Contract.Ensures(Contract.Result<int>() == weight);

return weight;}

public void AddKgs(int kgs){ Contract.Requires(kgs >= 0); Contract.Requires(weight+kgs >= 0); Contract.Ensures(weight == Contract.OldValue(weight) + kgs); weight = weight + kgs;}public Person(String n){ Contract.Requires(n != null &&

!n.Equals("")); Contract.Ensures(n.Equals(name)

&& weight == 0); name = n; weight = }

Specification and implementation are

bundled together. This is not nice!!!

Page 6: FEN 2013-04-07UCN T&B - PBA/CodeContract- Intro 1 Code Contract Introduction Specification of a Person Class

FEN 2013-04-07 UCN T&B - PBA/CodeContract-Intro 6

Separate specification and implementation[ContractClass(typeof(IPersonContract))]interface Iperson{

///<summary> ///@ also ///@ ensures \result != null; ///</summary> [Pure] String ToString(); ///<summary> ///@ ensures \result >= 0; ///</summary> [Pure] //Contract.Ensures(Contract.Result<int>() >= 0); int GetWeight(); ///<summary> /// /*@ requires kgs >= 0; /// @ ensures getWeight() == (\old(getWeight()) + kgs); /// @*/ ///</summary> void AddKgs(int kgs);}

What we would like:Specification in an

interface

But specs in Code Contract are method

calls, and method calls are not allowed in

interfaces...?

Telling that here is a contract

Page 7: FEN 2013-04-07UCN T&B - PBA/CodeContract- Intro 1 Code Contract Introduction Specification of a Person Class

FEN 2013-04-07 UCN T&B - PBA/CodeContract-Intro 7

[ContractClassFor(typeof(IPerson))]internal abstract class IPersonContract : IPerson{ [ContractInvariantMethod] private void ObjectInvariant() { Contract.Invariant(GetWeight() >= 0); } public override String ToString() { Contract.Ensures(Contract.Result<string>()

!= null); return default(string); } public int GetWeight() { Contract.Ensures(Contract.Result<int>() >=0); return default(int); } public void AddKgs(int kgs) { Contract.Requires(kgs >= 0); Contract.Requires(GetWeight()+kgs >= 0); Contract.Ensures(GetWeight() ==

Contract.OldValue(GetWeight()) + kgs); }}

Spec in internal abstract class with

dummy implementation

interface Iperson{ [Pure] String ToString(); int GetWeight(); void AddKgs(int kgs);}

Type invariant

Page 8: FEN 2013-04-07UCN T&B - PBA/CodeContract- Intro 1 Code Contract Introduction Specification of a Person Class

FEN 2013-04-07 UCN T&B - PBA/CodeContract-Intro 8

class Person: Iperson{ [ContractInvariantMethod] private void ObjectInvariant() { Contract.Invariant(!name.Equals("“) && name!= null && weight >= 0);

} private String name; private int weight; public Person(String n) { Contract.Requires(n != null && !n.Equals("")); Contract.Ensures(n.Equals(name) && weight == 0); name = n; weight = 0; }

Implementation in the class

Representation invariant

public override String ToString(){ Contract.Ensures(Contract.Result<string>()!= null); return "Person(\"" + name + "\"," + weight + ")";}public int GetWeight(){ Contract.Ensures(Contract.Result<int>() == weight); return weight;}public void AddKgs(int kgs){ Contract.Ensures(weight == Contract.OldValue(weight) + kgs); weight = weight + kgs;}

Constructor must establish the

invariant

Page 9: FEN 2013-04-07UCN T&B - PBA/CodeContract- Intro 1 Code Contract Introduction Specification of a Person Class

FEN 2013-04-07 UCN T&B - PBA/CodeContract-Intro 9

static void Main(string[] args){ IPerson p = new Person("Kurt"); Console.WriteLine(p.ToString()); p.AddKgs(99); Console.WriteLine("GetWeight: "+p.GetWeight()); Console.WriteLine(p.ToString()); Console.ReadLine();

p.AddKgs(-9); Console.ReadLine(); Console.WriteLine(p.ToString()); IPerson pp = new Person(""); Console.WriteLine(pp.ToString()); Console.ReadLine();}

interface as static typeclass as dynamic type