{"id":1435,"date":"2021-11-27T22:01:20","date_gmt":"2021-11-27T21:01:20","guid":{"rendered":"https:\/\/www.blauringlabs.com\/?p=1435"},"modified":"2023-01-23T18:31:41","modified_gmt":"2023-01-23T17:31:41","slug":"law-of-demeter-principle-of-least-knowledge","status":"publish","type":"post","link":"https:\/\/www.blauringlabs.com\/en\/law-of-demeter-principle-of-least-knowledge\/","title":{"rendered":"Law of Demeter or Principle of Least Knowledge"},"content":{"rendered":"<p>One of the classical as well as mainly ignored principles of software engineering is the Principle of Least Knowledge aka&nbsp;<em>Law of Demeter<\/em>. There is many academical essays in the web about this, but the main point it\u2019s not so easy to grasp in my opinion, so I\u2019ll give a shot in explaining this concept from a developer perspective.<\/p>\n<p>Imagine a class&nbsp;<em>Customer<\/em>&nbsp;that offers a pointer to class&nbsp;<em>Wallet<\/em>, so for each payment, the Customer just delegates into&nbsp;<em>Wallet<\/em>.<\/p>\n<div class=\"language-c++ highlighter-rouge\">\n<div class=\"highlight\">\n<pre class=\"highlight\"><code><span class=\"k\">class<\/span> <span class=\"nc\">Customer<\/span> \n<span class=\"p\">{<\/span>\n<span class=\"nl\">public:<\/span>\n<span class=\"n\">Customer<\/span><span class=\"p\">()<\/span> <span class=\"p\">{<\/span>\n        <span class=\"n\">myWallet<\/span> <span class=\"o\">=<\/span> <span class=\"k\">new<\/span> <span class=\"n\">Wallet<\/span><span class=\"p\">();<\/span>\n        <span class=\"n\">myWallet<\/span><span class=\"o\">-&gt;<\/span><span class=\"n\">addMoney<\/span><span class=\"p\">(<\/span><span class=\"mi\">200<\/span><span class=\"p\">);<\/span>\n <span class=\"p\">}<\/span>\n\n<span class=\"o\">~<\/span><span class=\"n\">Customer<\/span><span class=\"p\">(){<\/span>  <span class=\"k\">delete<\/span> <span class=\"n\">myWallet<\/span><span class=\"p\">;<\/span> <span class=\"p\">}<\/span>\n\n<span class=\"n\">Wallet<\/span><span class=\"o\">*<\/span> <span class=\"n\">getWallet<\/span><span class=\"p\">()<\/span> <span class=\"p\">{<\/span> <span class=\"k\">return<\/span> <span class=\"n\">myWallet<\/span><span class=\"p\">;<\/span> <span class=\"p\">}<\/span>\n\n<span class=\"nl\">private:<\/span>\n    <span class=\"n\">Wallet<\/span><span class=\"o\">*<\/span> <span class=\"n\">myWallet<\/span><span class=\"p\">;<\/span>\n<span class=\"p\">};<\/span>\n<\/code><\/pre>\n<\/div>\n<\/div>\n<p>and the class Wallet takes care of the cash by itself:<\/p>\n<div class=\"language-c++ highlighter-rouge\">\n<div class=\"highlight\">\n<pre class=\"highlight\"><code><span class=\"k\">class<\/span> <span class=\"nc\">Wallet<\/span> \n<span class=\"p\">{<\/span>\n<span class=\"nl\">public:<\/span>\n    <span class=\"n\">Wallet<\/span><span class=\"p\">()<\/span>\n    <span class=\"o\">:<\/span><span class=\"n\">currentMoney<\/span><span class=\"p\">(<\/span><span class=\"mi\">0<\/span><span class=\"p\">)<\/span>\n    <span class=\"p\">{}<\/span>\n\n    <span class=\"kt\">void<\/span> <span class=\"n\">addMoney<\/span><span class=\"p\">(<\/span><span class=\"kt\">int<\/span> <span class=\"n\">amount<\/span><span class=\"p\">)<\/span> <span class=\"p\">{<\/span>\n        <span class=\"n\">currentMoney<\/span> <span class=\"o\">+=<\/span> <span class=\"n\">amount<\/span><span class=\"p\">;<\/span>\n    <span class=\"p\">}<\/span>\n\n    <span class=\"k\">const<\/span> <span class=\"kt\">int<\/span> <span class=\"n\">howMuchMoney<\/span><span class=\"p\">()<\/span> <span class=\"p\">{<\/span>\n        <span class=\"k\">return<\/span> <span class=\"n\">currentMoney<\/span><span class=\"p\">;<\/span>\n    <span class=\"p\">}<\/span>\n\n    <span class=\"kt\">int<\/span> <span class=\"n\">retrieveMoney<\/span><span class=\"p\">(<\/span><span class=\"kt\">int<\/span> <span class=\"n\">amount<\/span><span class=\"p\">)<\/span> <span class=\"p\">{<\/span>\n       <span class=\"kt\">int<\/span> <span class=\"n\">moneyTaken<\/span><span class=\"p\">;<\/span>\n       <span class=\"k\">if<\/span> <span class=\"p\">(<\/span><span class=\"n\">amount<\/span> <span class=\"o\">&lt;=<\/span> <span class=\"n\">currentMoney<\/span><span class=\"p\">)<\/span> <span class=\"p\">{<\/span>\n           <span class=\"n\">moneyTaken<\/span> <span class=\"o\">=<\/span> <span class=\"n\">amount<\/span><span class=\"p\">;<\/span>\n           <span class=\"n\">currentMoney<\/span> <span class=\"o\">-=<\/span> <span class=\"n\">amount<\/span><span class=\"p\">;<\/span>\n       <span class=\"p\">}<\/span>\n       <span class=\"k\">else<\/span> <span class=\"p\">{<\/span>\n           <span class=\"n\">moneyTaken<\/span> <span class=\"o\">=<\/span> <span class=\"n\">currentMoney<\/span><span class=\"p\">;<\/span>\n           <span class=\"n\">currentMoney<\/span> <span class=\"o\">=<\/span> <span class=\"mi\">0<\/span><span class=\"p\">;<\/span>\n       <span class=\"p\">}<\/span>\n       <span class=\"k\">return<\/span> <span class=\"n\">moneyTaken<\/span><span class=\"p\">;<\/span>\n    <span class=\"p\">}<\/span>\n\n<span class=\"nl\">private:<\/span>\n    <span class=\"kt\">int<\/span> <span class=\"n\">currentMoney<\/span><span class=\"p\">;<\/span>\n<span class=\"p\">};<\/span>\n<\/code><\/pre>\n<\/div>\n<\/div>\n<p>For each payment,&nbsp;<em>Customer<\/em>&nbsp;just delegates to&nbsp;<em>Wallet<\/em>, as you see in the following lines:<\/p>\n<div class=\"language-c++ highlighter-rouge\">\n<div class=\"highlight\">\n<pre class=\"highlight\"><code><span class=\"kt\">int<\/span> <span class=\"nf\">main<\/span><span class=\"p\">()<\/span>\n\n<span class=\"p\">{<\/span>\n\n<span class=\"n\">Customer<\/span> <span class=\"n\">customer<\/span><span class=\"p\">;<\/span>\n<span class=\"kt\">int<\/span>  <span class=\"n\">customerMoney<\/span> <span class=\"o\">=<\/span> <span class=\"n\">customer<\/span><span class=\"p\">.<\/span><span class=\"n\">getWallet<\/span><span class=\"p\">()<\/span><span class=\"o\">-&gt;<\/span><span class=\"n\">howMuchMoney<\/span><span class=\"p\">();<\/span>\n\n<span class=\"n\">std<\/span><span class=\"o\">::<\/span><span class=\"n\">cout<\/span> <span class=\"o\">&lt;&lt;<\/span> <span class=\"s\">\"Money, \"<\/span> <span class=\"o\">&lt;&lt;<\/span> <span class=\"n\">customerMoney<\/span> <span class=\"o\">&lt;&lt;<\/span> <span class=\"s\">\"!<\/span><span class=\"se\">\\n<\/span><span class=\"s\">\"<\/span><span class=\"p\">;<\/span> <span class=\"c1\">\/\/ Money, 200!<\/span>\n\n<span class=\"c1\">\/\/Buy<\/span>\n<span class=\"kt\">bool<\/span> <span class=\"n\">waspaid<\/span> <span class=\"o\">=<\/span> <span class=\"n\">customer<\/span><span class=\"p\">.<\/span><span class=\"n\">getWallet<\/span><span class=\"p\">()<\/span><span class=\"o\">-&gt;<\/span><span class=\"n\">retrieveMoney<\/span><span class=\"p\">(<\/span><span class=\"mi\">3<\/span><span class=\"p\">);<\/span>\n\n<span class=\"n\">std<\/span><span class=\"o\">::<\/span><span class=\"n\">cout<\/span> <span class=\"o\">&lt;&lt;<\/span> <span class=\"s\">\"paid, \"<\/span> <span class=\"o\">&lt;&lt;<\/span> <span class=\"p\">(<\/span><span class=\"n\">waspaid<\/span><span class=\"o\">?<\/span><span class=\"s\">\"yes\"<\/span><span class=\"o\">:<\/span><span class=\"s\">\"no\"<\/span><span class=\"p\">)<\/span> <span class=\"o\">&lt;&lt;<\/span> <span class=\"s\">\"!<\/span><span class=\"se\">\\n<\/span><span class=\"s\">\"<\/span><span class=\"p\">;<\/span> <span class=\"c1\">\/\/paid, yes!<\/span>\n<span class=\"n\">std<\/span><span class=\"o\">::<\/span><span class=\"n\">cout<\/span> <span class=\"o\">&lt;&lt;<\/span> <span class=\"s\">\"current Money, \"<\/span> <span class=\"o\">&lt;&lt;<\/span> <span class=\"n\">customer<\/span><span class=\"p\">.<\/span><span class=\"n\">getWallet<\/span><span class=\"p\">()<\/span><span class=\"o\">-&gt;<\/span><span class=\"n\">howMuchMoney<\/span><span class=\"p\">()<\/span> <span class=\"o\">&lt;&lt;<\/span> <span class=\"s\">\"!<\/span><span class=\"se\">\\n<\/span><span class=\"s\">\"<\/span><span class=\"p\">;<\/span> \n<span class=\"c1\">\/\/current Money, 197!<\/span>\n\n<span class=\"p\">}<\/span>\n<\/code><\/pre>\n<\/div>\n<\/div>\n<p>So far so good. By just calling&nbsp;<em>customer.getWallet()<\/em>&nbsp;class Customer shifts the work to&nbsp;<em>Wallet<\/em>. As&nbsp;<em>Wallet<\/em>&nbsp;know how to deal with the cash flow, all is well.<\/p>\n<p>Well?, well, let\u2019s say in an update,&nbsp;<em>Customer<\/em>&nbsp;has to deal with 2 Wallets (I\u2019m old enough to remember the times before \u20ac, when I had to carry 2 wallets around, one with Spanish Pesetas and other with German D-Marks. Fortunately not anymore). Translating that to our code, it means the&nbsp;<em>Customer<\/em>&nbsp;need a second instance of&nbsp;<em>Wallet<\/em>, a situation we can code like this:<\/p>\n<div class=\"language-c++ highlighter-rouge\">\n<div class=\"highlight\">\n<pre class=\"highlight\"><code><span class=\"k\">class<\/span> <span class=\"nc\">Customer<\/span> <span class=\"p\">{<\/span>\n\n<span class=\"nl\">public:<\/span>\n    <span class=\"n\">Customer<\/span><span class=\"p\">()<\/span> <span class=\"p\">{<\/span>\n        <span class=\"n\">myWallets<\/span><span class=\"p\">.<\/span><span class=\"n\">push_back<\/span><span class=\"p\">(<\/span><span class=\"k\">new<\/span> <span class=\"n\">Wallet<\/span><span class=\"p\">());<\/span>\n        <span class=\"n\">myWallets<\/span><span class=\"p\">.<\/span><span class=\"n\">push_back<\/span><span class=\"p\">(<\/span><span class=\"k\">new<\/span> <span class=\"n\">Wallet<\/span><span class=\"p\">());<\/span>\n        <span class=\"n\">myWallets<\/span><span class=\"p\">[<\/span><span class=\"mi\">0<\/span><span class=\"p\">]<\/span><span class=\"o\">-&gt;<\/span><span class=\"n\">addMoney<\/span><span class=\"p\">(<\/span><span class=\"mi\">200<\/span><span class=\"p\">);<\/span>\n        <span class=\"n\">myWallets<\/span><span class=\"p\">[<\/span><span class=\"mi\">1<\/span><span class=\"p\">]<\/span><span class=\"o\">-&gt;<\/span><span class=\"n\">addMoney<\/span><span class=\"p\">(<\/span><span class=\"mi\">50<\/span><span class=\"p\">);<\/span>\n    <span class=\"p\">}<\/span>\n\n<span class=\"o\">~<\/span><span class=\"n\">Customer<\/span><span class=\"p\">(){<\/span>\n  <span class=\"k\">for<\/span> <span class=\"p\">(<\/span><span class=\"n\">std<\/span><span class=\"o\">::<\/span><span class=\"n\">vector<\/span><span class=\"o\">&lt;<\/span><span class=\"n\">Wallet<\/span><span class=\"o\">*&gt;::<\/span><span class=\"n\">iterator<\/span> <span class=\"n\">it<\/span> <span class=\"o\">=<\/span> <span class=\"n\">myWallets<\/span><span class=\"p\">.<\/span><span class=\"n\">begin<\/span><span class=\"p\">()<\/span> <span class=\"p\">;<\/span> <span class=\"n\">it<\/span> <span class=\"o\">!=<\/span> <span class=\"n\">myWallets<\/span><span class=\"p\">.<\/span><span class=\"n\">end<\/span><span class=\"p\">();<\/span> <span class=\"o\">++<\/span><span class=\"n\">it<\/span><span class=\"p\">)<\/span>\n     <span class=\"k\">delete<\/span><span class=\"p\">(<\/span><span class=\"o\">*<\/span><span class=\"n\">it<\/span><span class=\"p\">);<\/span>\n<span class=\"p\">}<\/span>\n\n<span class=\"n\">Wallet<\/span><span class=\"o\">*<\/span> <span class=\"n\">getWallet<\/span><span class=\"p\">(<\/span><span class=\"kt\">unsigned<\/span> <span class=\"kt\">int<\/span> <span class=\"n\">pos<\/span><span class=\"p\">)<\/span> <span class=\"p\">{<\/span>\n        <span class=\"k\">if<\/span> <span class=\"p\">(<\/span><span class=\"n\">pos<\/span> <span class=\"o\">&lt;<\/span> <span class=\"mi\">2<\/span><span class=\"p\">)<\/span>\n            <span class=\"k\">return<\/span> <span class=\"n\">myWallets<\/span><span class=\"p\">[<\/span><span class=\"n\">pos<\/span><span class=\"p\">];<\/span>\n        <span class=\"k\">else<\/span>\n            <span class=\"k\">return<\/span> <span class=\"nb\">NULL<\/span><span class=\"p\">;<\/span>\n        <span class=\"p\">}<\/span>\n\n<span class=\"nl\">private:<\/span>\n       <span class=\"n\">std<\/span><span class=\"o\">::<\/span><span class=\"n\">vector<\/span><span class=\"o\">&lt;<\/span><span class=\"n\">Wallet<\/span><span class=\"o\">*&gt;<\/span> <span class=\"n\">myWallets<\/span><span class=\"p\">;<\/span>\n<span class=\"p\">};<\/span>\n<\/code><\/pre>\n<\/div>\n<\/div>\n<p>But now, the code inside Main() is broken. We need to rewrite it and tell&nbsp;<em>which Wallet<\/em>&nbsp;to get the money from.<\/p>\n<div class=\"language-c++ highlighter-rouge\">\n<div class=\"highlight\">\n<pre class=\"highlight\"><code><span class=\"kt\">int<\/span> <span class=\"nf\">main<\/span><span class=\"p\">()<\/span>\n<span class=\"p\">{<\/span>\n  <span class=\"n\">Customer<\/span> <span class=\"n\">customer<\/span><span class=\"p\">;<\/span>\n  <span class=\"kt\">int<\/span> <span class=\"n\">customerMoney<\/span> <span class=\"o\">=<\/span> <span class=\"n\">customer<\/span><span class=\"p\">.<\/span><span class=\"n\">getWallet<\/span><span class=\"p\">(<\/span><span class=\"mi\">0<\/span><span class=\"p\">)<\/span><span class=\"o\">-&gt;<\/span><span class=\"n\">getCurrentMoney<\/span><span class=\"p\">();<\/span>\n  <span class=\"n\">std<\/span><span class=\"o\">::<\/span><span class=\"n\">cout<\/span> <span class=\"o\">&lt;&lt;<\/span> <span class=\"s\">\"Money, \"<\/span> <span class=\"o\">&lt;&lt;<\/span> <span class=\"n\">customerMoney<\/span> <span class=\"o\">&lt;&lt;<\/span> <span class=\"s\">\"!<\/span><span class=\"se\">\\n<\/span><span class=\"s\">\"<\/span><span class=\"p\">;<\/span> <span class=\"c1\">\/\/Money, 200!<\/span>\n<span class=\"p\">}<\/span>\n<\/code><\/pre>\n<\/div>\n<\/div>\n<p>You can imagine that&nbsp;<strong>all<\/strong>&nbsp;places where&nbsp;<em>customer.GetWallet()<\/em>&nbsp;is invoked now need correction. And depending of your code, this can be a lot of work. It\u2019s even worse if&nbsp;<em>Customer<\/em>&nbsp;is shipped as part of a library and you have no access to the code which makes use of the&nbsp;<em>Wallet<\/em>.<\/p>\n<p>This is not only a design flow, but sometimes also a security issue. You cannot assume that clients use your API in the way you expect:<\/p>\n<div class=\"language-c++ highlighter-rouge\">\n<div class=\"highlight\">\n<pre class=\"highlight\"><code><span class=\"kt\">int<\/span> <span class=\"nf\">main<\/span><span class=\"p\">()<\/span>\n<span class=\"p\">{<\/span>\n  <span class=\"c1\">\/\/Opps!<\/span>\n  <span class=\"n\">Customer<\/span><span class=\"o\">*<\/span> <span class=\"n\">victim<\/span> <span class=\"o\">=<\/span> <span class=\"o\">&amp;<\/span><span class=\"n\">customer<\/span><span class=\"p\">;<\/span>\n  <span class=\"n\">victim<\/span><span class=\"o\">-&gt;<\/span><span class=\"n\">getWallet<\/span><span class=\"p\">()<\/span><span class=\"o\">-&gt;<\/span><span class=\"n\">retrieveMoney<\/span><span class=\"p\">(<\/span><span class=\"n\">victim<\/span><span class=\"o\">-&gt;<\/span><span class=\"n\">getWallet<\/span><span class=\"p\">()<\/span><span class=\"o\">-&gt;<\/span><span class=\"n\">howMuchMoney<\/span><span class=\"p\">());<\/span>\n  <span class=\"n\">std<\/span><span class=\"o\">::<\/span><span class=\"n\">cout<\/span> <span class=\"o\">&lt;&lt;<\/span> <span class=\"s\">\"Money left?, \"<\/span> <span class=\"o\">&lt;&lt;<\/span> <span class=\"n\">victim<\/span><span class=\"o\">-&gt;<\/span><span class=\"n\">getWallet<\/span><span class=\"p\">()<\/span><span class=\"o\">-&gt;<\/span><span class=\"n\">howMuchMoney<\/span><span class=\"p\">()<\/span> <span class=\"o\">&lt;&lt;<\/span> <span class=\"s\">\"!<\/span><span class=\"se\">\\n<\/span><span class=\"s\">\"<\/span><span class=\"p\">;<\/span> \n  <span class=\"c1\">\/\/Money left?, 0!<\/span>\n<span class=\"p\">}<\/span>\n<\/code><\/pre>\n<\/div>\n<\/div>\n<p>But wait a second, why should&nbsp;<em>Main()<\/em>&nbsp;have to choose between wallets? Why should it know that there are two? This imply a level of knowledge that no one from outside&nbsp;<em>Customer<\/em>&nbsp;class should know. What\u2019s the problem here?<\/p>\n<ul>\n<li>We are exposing customer\u2019s internal structure.<\/li>\n<li>There is a high coupling between Wallet and customer\u2019s clients.<\/li>\n<li>The relationship&nbsp;<em>has-a<\/em>&nbsp;between&nbsp;<em>Customer<\/em>&nbsp;and&nbsp;<em>Wallet<\/em>&nbsp;is&nbsp;<em>de facto<\/em>&nbsp;part of the Customer interface to the outside world.<\/li>\n<\/ul>\n<p>To sum up: We are breaking the Law of Demeter.<\/p>\n<h3 id=\"law-of-demeter\">Law of Demeter<\/h3>\n<p>According to&nbsp;<a href=\"https:\/\/en.wikipedia.org\/wiki\/Law_of_Demeter\">Wikipedia<\/a>, The Law of Demeter for functions requires that a method&nbsp;<strong>m<\/strong>&nbsp;of an object&nbsp;<strong>O<\/strong>&nbsp;may only invoke the methods of the following kinds of objects:<\/p>\n<div class=\"language-plaintext highlighter-rouge\">\n<div class=\"highlight\">\n<pre class=\"highlight\"><code>O itself\nm's parameters\nAny objects created\/instantiated within m\nO's direct component objects\nA global variable, accessible by O, in the scope of m\n<\/code><\/pre>\n<\/div>\n<\/div>\n<p>In particular, an object should avoid invoking methods of a member object returned by another method. Demeter law set restrictions on the&nbsp;<strong>Types<\/strong>&nbsp;of objects we can talk with. In side a method, we can only talk to&nbsp;<em>friends<\/em>:<\/p>\n<div class=\"language-plaintext highlighter-rouge\">\n<div class=\"highlight\">\n<pre class=\"highlight\"><code>Myself\nMethod parameters\nObjects created by the method\nDirect components of my class\nGlobal variables\n<\/code><\/pre>\n<\/div>\n<\/div>\n<p>All other Types are&nbsp;<em>strangers<\/em>. It\u2019s not allowed invoking method of an object returned by another method: The friends of my friends are strangers to me.<\/p>\n<p>In the code snipped above, class&nbsp;<em>Wallet<\/em>&nbsp;is clearly a strange for&nbsp;<em>Main()<\/em>&nbsp;method.<\/p>\n<p>Note: The concept of friend is used here as in plain language. Nothing to do with the keyword&nbsp;<em>friend<\/em>&nbsp;in c++<\/p>\n<h3 id=\"keeping-the-law\">Keeping the Law<\/h3>\n<p>For a better maintenance, it\u2019s better to rewrite the code to abstract&nbsp;<em>Wallet<\/em>&nbsp;away, so&nbsp;<em>Customer<\/em>&nbsp;offers 2 methods:<\/p>\n<div class=\"language-plaintext highlighter-rouge\">\n<div class=\"highlight\">\n<pre class=\"highlight\"><code>HowMuchMoney\nPay\n<\/code><\/pre>\n<\/div>\n<\/div>\n<p>while the&nbsp;<em>Wallet<\/em>&nbsp;itself remains unexposed.<\/p>\n<div class=\"language-c++ highlighter-rouge\">\n<div class=\"highlight\">\n<pre class=\"highlight\"><code><span class=\"k\">class<\/span> <span class=\"nc\">Customer<\/span> <span class=\"p\">{<\/span>\n\n<span class=\"nl\">public:<\/span>\n    <span class=\"n\">Customer<\/span><span class=\"p\">()<\/span> <span class=\"p\">{<\/span>\n        <span class=\"n\">myWallet<\/span> <span class=\"o\">=<\/span> <span class=\"k\">new<\/span> <span class=\"n\">Wallet<\/span><span class=\"p\">();<\/span>\n        <span class=\"n\">myWallet<\/span><span class=\"o\">-&gt;<\/span><span class=\"n\">addMoney<\/span><span class=\"p\">(<\/span><span class=\"mi\">200<\/span><span class=\"p\">);<\/span>\n    <span class=\"p\">}<\/span>\n\n<span class=\"o\">~<\/span><span class=\"n\">Customer<\/span><span class=\"p\">(){<\/span>  <span class=\"k\">delete<\/span> <span class=\"n\">myWallet<\/span><span class=\"p\">;<\/span> <span class=\"p\">}<\/span>\n\n<span class=\"k\">const<\/span> <span class=\"kt\">int<\/span> <span class=\"n\">howMuchMoney<\/span><span class=\"p\">()<\/span> <span class=\"p\">{<\/span>\n    <span class=\"k\">return<\/span> <span class=\"n\">myWallet<\/span><span class=\"o\">-&gt;<\/span><span class=\"n\">howMuchMoney<\/span><span class=\"p\">();<\/span>\n<span class=\"p\">}<\/span>\n\n<span class=\"kt\">int<\/span> <span class=\"n\">pay<\/span><span class=\"p\">(<\/span><span class=\"kt\">int<\/span> <span class=\"n\">amount<\/span><span class=\"p\">)<\/span> <span class=\"p\">{<\/span>\n <span class=\"k\">return<\/span> <span class=\"n\">myWallet<\/span><span class=\"o\">-&gt;<\/span><span class=\"n\">retrieveMoney<\/span><span class=\"p\">(<\/span><span class=\"n\">amount<\/span><span class=\"p\">);<\/span>\n<span class=\"p\">}<\/span>\n\n<span class=\"nl\">private:<\/span>\n    <span class=\"n\">Wallet<\/span><span class=\"o\">*<\/span> <span class=\"n\">myWallet<\/span><span class=\"p\">;<\/span>\n<span class=\"p\">};<\/span>\n\n<span class=\"k\">class<\/span> <span class=\"nc\">Wallet<\/span> \n<span class=\"p\">{<\/span>\n<span class=\"nl\">public:<\/span>\n    <span class=\"n\">Wallet<\/span><span class=\"p\">()<\/span>\n    <span class=\"o\">:<\/span><span class=\"n\">currentMoney<\/span><span class=\"p\">(<\/span><span class=\"mi\">0<\/span><span class=\"p\">)<\/span>\n    <span class=\"p\">{}<\/span>\n\n    <span class=\"kt\">void<\/span> <span class=\"n\">addMoney<\/span><span class=\"p\">(<\/span><span class=\"kt\">int<\/span> <span class=\"n\">amount<\/span><span class=\"p\">)<\/span> <span class=\"p\">{<\/span>\n        <span class=\"n\">currentMoney<\/span> <span class=\"o\">+=<\/span> <span class=\"n\">amount<\/span><span class=\"p\">;<\/span>\n    <span class=\"p\">}<\/span>\n\n    <span class=\"k\">const<\/span> <span class=\"kt\">int<\/span> <span class=\"n\">howMuchMoney<\/span><span class=\"p\">()<\/span> <span class=\"p\">{<\/span>\n        <span class=\"k\">return<\/span> <span class=\"n\">currentMoney<\/span><span class=\"p\">;<\/span>\n    <span class=\"p\">}<\/span>\n\n    <span class=\"kt\">int<\/span> <span class=\"n\">retrieveMoney<\/span><span class=\"p\">(<\/span><span class=\"kt\">int<\/span> <span class=\"n\">amount<\/span><span class=\"p\">)<\/span> <span class=\"p\">{<\/span>\n       <span class=\"kt\">int<\/span> <span class=\"n\">moneyTaken<\/span><span class=\"p\">;<\/span>\n       <span class=\"k\">if<\/span> <span class=\"p\">(<\/span><span class=\"n\">amount<\/span> <span class=\"o\">&lt;=<\/span> <span class=\"n\">currentMoney<\/span><span class=\"p\">)<\/span> <span class=\"p\">{<\/span>\n           <span class=\"n\">moneyTaken<\/span> <span class=\"o\">=<\/span> <span class=\"n\">amount<\/span><span class=\"p\">;<\/span>\n           <span class=\"n\">currentMoney<\/span> <span class=\"o\">-=<\/span> <span class=\"n\">amount<\/span><span class=\"p\">;<\/span>\n       <span class=\"p\">}<\/span>\n       <span class=\"k\">else<\/span> <span class=\"p\">{<\/span>\n           <span class=\"n\">moneyTaken<\/span> <span class=\"o\">=<\/span> <span class=\"n\">currentMoney<\/span><span class=\"p\">;<\/span>\n           <span class=\"n\">currentMoney<\/span> <span class=\"o\">=<\/span> <span class=\"mi\">0<\/span><span class=\"p\">;<\/span>\n       <span class=\"p\">}<\/span>\n\n       <span class=\"k\">return<\/span> <span class=\"n\">moneyTaken<\/span><span class=\"p\">;<\/span>\n    <span class=\"p\">}<\/span>\n\n<span class=\"nl\">private:<\/span>\n\n    <span class=\"kt\">int<\/span> <span class=\"n\">currentMoney<\/span><span class=\"p\">;<\/span>\n<span class=\"p\">};<\/span>\n\n<\/code><\/pre>\n<\/div>\n<\/div>\n<h3 id=\"why-is-this-way-better\">Why is this way better?<\/h3>\n<p>You can argue that we added more complexity in&nbsp;<em>Customer<\/em>&nbsp;class and some method of Customer class are just wrapper of&nbsp;<em>Wallet<\/em>\u2019s ones. Yes, that the price of abstraction. In return, you get<\/p>\n<ul>\n<li>Code easier to understand: the Customer clients do not need to know about the relationship between Customer and Wallet.<\/li>\n<li>Better maintainability: If the customer decides to change the Wallet for a payment App, the customer\u2019s client remain unaffected. also changes in the interface of the Wallet does not propagate to the clients of Customer.<\/li>\n<\/ul>\n<p>But at the end, this models better the relationship in the real world. Do you handover your wallet to the shop assistant at the market when you buy your stuff? I bet you don\u2019t. Instead you handle your wallet by yourself. It\u2019s more&nbsp;<em>complex<\/em>, as you have to take the cash, check the change, and so on, but for all of us, this effort pays off.<\/p>\n<p>So it should be in software design.<\/p>\n<h3 id=\"references\">References<\/h3>\n<ol>\n<li>Original paper: <a href=\"http:\/\/www.ccs.neu.edu\/research\/demeter\/papers\/law-of-demeter\/oopsla88-law-of-demeter.pdf\">http:\/\/www.ccs.neu.edu\/research\/demeter\/papers\/law-of-demeter\/oopsla88-law-of-demeter.pdf<\/a><\/li>\n<li>\u201cThe Paperboy, The Wallet,and The Law Of Demeter\u201d . D Bock<\/li>\n<li>\u201cAn Empirical Validation of the Benefits of Adhering to the Law of Demeter\u201d.Guo, W\u00fcrsch, Giger and Gall.<\/li>\n<li><a href=\"https:\/\/en.wikipedia.org\/wiki\/Law_of_Demeter\">https:\/\/en.wikipedia.org\/wiki\/Law_of_Demeter<\/a><\/li>\n<li><a href=\"https:\/\/pragprog.com\/articles\/tell-dont-ask\">https:\/\/pragprog.com\/articles\/tell-dont-ask<\/a><\/li>\n<\/ol>\n","protected":false},"excerpt":{"rendered":"<p>One of the classical as well as mainly ignored principles of software engineering is the Principle of Least Knowledge aka&nbsp;Law of Demeter. There is many academical essays in the web about this, but the main point it\u2019s not\u2026<\/p>\n","protected":false},"author":2,"featured_media":1538,"comment_status":"closed","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"pgc_meta":"","footnotes":""},"categories":[19,20,14],"tags":[],"class_list":["post-1435","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-c-en","category-development-en","category-uncategorized"],"acf":[],"_links":{"self":[{"href":"https:\/\/www.blauringlabs.com\/en\/wp-json\/wp\/v2\/posts\/1435","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.blauringlabs.com\/en\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.blauringlabs.com\/en\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.blauringlabs.com\/en\/wp-json\/wp\/v2\/users\/2"}],"replies":[{"embeddable":true,"href":"https:\/\/www.blauringlabs.com\/en\/wp-json\/wp\/v2\/comments?post=1435"}],"version-history":[{"count":4,"href":"https:\/\/www.blauringlabs.com\/en\/wp-json\/wp\/v2\/posts\/1435\/revisions"}],"predecessor-version":[{"id":1536,"href":"https:\/\/www.blauringlabs.com\/en\/wp-json\/wp\/v2\/posts\/1435\/revisions\/1536"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/www.blauringlabs.com\/en\/wp-json\/wp\/v2\/media\/1538"}],"wp:attachment":[{"href":"https:\/\/www.blauringlabs.com\/en\/wp-json\/wp\/v2\/media?parent=1435"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.blauringlabs.com\/en\/wp-json\/wp\/v2\/categories?post=1435"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.blauringlabs.com\/en\/wp-json\/wp\/v2\/tags?post=1435"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}