Answer to Question #233213 in MatLAB for Patel parth

Question #233213
A simple card game such as twenty-one
(Link for refreshing : https://en.wikipedia.org/wiki/Twenty-One_(card_game))

This is criteria :
The code that you use to produce that application must use a combination of at least two of:

Loops
Vectors or Arrays
Conditional execution
Optionally, your code might embed:

Functions.
Visualisation of data
1
Expert's answer
2021-09-05T08:24:39-0400
   basebet = 10;
   if nargin == 0
      P1 = [];
      P2 = [];
      D = [];
      bet1 = 0;
      bet2 = 0;
      count = 0;
      total = 0;
      who = 1;
      buttons = initbuttons;
      setbuttons({'Double','Stand','Hit'})
      set(gcf,'userdata',{P1,P2,D,bet1,bet2,count,total,who,buttons})
      action = 'Deal';
   end
   
   userdata = get(gcf,'userdata');
   [P1,P2,D,bet1,bet2,count,total,who,buttons] = deal(userdata{:});
   switch action
      case 'Deal'
         setup;
      case 'Hit'
         hit
      case 'Stand'
         stand
      case 'Keep'
         keep
      case 'Double'
         double
      case 'Split'
         split
      case 'Close'
         close(gcf)
         return 
   end
   set(gcf,'userdata',{P1,P2,D,bet1,bet2,count,total,who,buttons})
  
   % ------------------------
     
   function c = card
      % Deal one card from a continuous shuffling machine
      c = ceil(52*rand);
   end
      
   % ------------------------
   function setup;
      delete(get(gca,'children'))
      bet1 = basebet;
      bet2 = 0;
      who = 1;
      P1 = card;         % Player's hand
      D = card;          % Dealer's hand
      P1 = [P1 card];
      D = [D -card];     % Hide dealer's hole card
      P2 = [];
      show(1,P1,false)
      show(3,D,false)
      if value(P1) == 21
         twentyone
      elseif mod(P1(1),13)==mod(P1(2),13);
         % Option to split pairs.
         setbuttons({'','Keep','Split'})
         strategy(P1,D,false)
      else
         setbuttons({'Double','Stand','Hit'})
         strategy(P1,D,false)
      end
      if total >= 0, sig = '+'; else, sig = '-'; end
      total_str = sprintf('%6.0f hands,  $ %c%d',count,sig,abs(total));
      text(-2.0,4.5,total_str,'tag','total','fontsize',20);
   end
   
   % ------------------------
   function hit
      if who == 1
         P1 = [P1 card];
         show(1,P1,false)
         if value(P1) >= 21
            stand
            return
         end
         if length(P1) > 2
            set(buttons(1),'enable','off')
         end
         strategy(P1,D,false)
      else
         P2 = [P2 card];
         show(2,P2,false)
         if value(P2) >= 21
            finish
            return
         end
         if length(P2) > 2
            set(buttons(1),'enable','off')
         end
         strategy(P2,D,false)
      end
   end
   % ------------------------
   function double
      if who == 1
         bet1 = 2*bet1;
         P1 = [P1 card];
         show(1,P1,~isempty(P2))
         if ~isempty(P2)
            P2 = [P2 card];
            show(2,P2,false)
            strategy(P2,D,false)
         end
         finish
         return
      else
         bet2 = 2*bet2;
         P2 = [P2 card];
         show(2,P2,false)
         finish
         return
      end
   end
   % ------------------------
   function split
      bet2 = bet1;
      P2 = P1(2);
      P1(2) = card;
      show(1,P1,false);
      show(2,P2,true);
      setbuttons({'Double','Stand','Hit'})
      if value(P1) >= 21
         stand
         return
      end
      strategy(P1,D,false)
   end
   % ------------------------
   function keep
      setbuttons({'Double','Stand','Hit'})
      strategy(P1,D,true)
   end
   % ------------------------
   function stand
      % Start to play second hand, if any
      if who == 1 && ~isempty(P2)
         who = 2;
         P2 = [P2 card];
         show(1,P1,true)
         show(2,P2,false)
         if value(P2) >= 21
            finish
            return
         end
         strategy(P2,D,false)
      else
         finish
         return
      end
   end
   % ------------------------
   
   function buttons = initbuttons
      clf
      shg
      rng('shuffle')
      axes('pos',[0 0 1 1])
      axis([-5 5 -5 5])
      axis off
      for k = 1:3
         buttons(k) = uicontrol('units','normal','style','pushbutton', ...
            'pos',[.23+.18*k .02 .16 .08],'fontweight','bold', ...
            'callback','blackjack(get(gco,''string''))');
      end
   end
   
   % ------------------------
     
   function setbuttons(B)
      % B is a cell array of strings.
      for k = 1:length(B)
         if isempty(B{k})
            set(buttons(k),'vis','off')
         else
            set(buttons(k),'string',B{k},'vis','on','enable','on', ...
               'foreground','black')
         end
      end
   end
   
   % ------------------------
     
   function strategy(P,D,kept)
      if length(P) == 2 && ~kept && mod(P(1),13) == mod(P(2),13)
         s = pair(value(P(1)),value(D(1)));
      elseif any(mod(P,13) == 1)
         s = soft(value(P)-11,value(D(1)));
      else
         s = hard(value(P),value(D(1)));
      end
      set(buttons,'foreground','black')
      k = mod(s+1,3)+1;
      set(buttons(k),'foreground','red')
   end
   % ------------------------
      
   function v = value(X)
      % Evaluate hand
      X = mod(X-1,13)+1;
      X = min(X,10);
      v = sum(X);
      % Promote soft ace
      if any(X==1) & v<=11
         v = v + 10;
      end
   end
      
   % ------------------------
   function twentyone
      if value(D) < 21
         pay1 = 1.5*bet1;
         result(1,P1,'BLACKJACK',pay1)
         update_total(pay1,0)
      else
         finish
         return
      end
   end
      
   % ------------------------
      
   function finish
      if who == 1 && ~isempty(P2)
         who = 2;
         return
      end
      if value(P1) <= 21 || (~isempty(P2) && value(P2) <= 21)
         % Play dealer's hand
         D(2) = -D(2);     % Reveal dealer's hole card
         while value(D) <= 16
            D = [D card];
         end
         show(3,D,false)
         result(3,D)
      end
      valD = value(D);
   
      pay1 = settle(1,P1,bet1,valD);
      if isempty(P2)
         pay2 = 0;
      else
         pay2 = settle(2,P2,bet2,valD);
      end
      update_total(pay1,pay2)
   end
      
   % ------------------------
   function result(w,P,str,pay)
      x = min(1.5*length(P)-4.5,2.6);
      y = 2.5*(2-w);
      if w == 3
         t = sprintf(' %2d',value(D));
      elseif pay > 0
         t = sprintf('%2d,  %s +%2d',value(P),str,pay);
      elseif pay < 0
         t = sprintf('%2d,  %s -%2d',value(P),str,-pay);
      else
         t = sprintf('%2d,  %s',value(P),str);
      end
      text(x,y,t,'fontsize',20)
   end
      
   % ------------------------
      
   function pay = settle(w,P,bet,valD)
      show(w,P,false)
      valP = value(P);
      if valP > 21
         pay = -bet;
         result(w,P,'BUST',pay)
      elseif valD > 21 || valP > valD
         pay = bet;
         result(w,P,'WIN',pay)
      elseif valD > valP
         pay = -bet;
         result(w,P,'LOSE',pay)
      else
         pay = 0;
         result(w,P,'PUSH',pay)
      end
   end
      
   % ------------------------
   function update_total(pay1,pay2)
      total = total + pay1 + pay2;
      count = count+1;
      if total >= 0, sig = '+'; else, sig = '-'; end
      if count == 1
         total_str = sprintf('%6.0f hand,  $ %c%d',count,sig,abs(total));
      else
         total_str = sprintf('%6.0f hands,  $ %c%d',count,sig,abs(total));
      end
      set(findobj('tag','total'),'string',total_str)
      setbuttons({'','Deal','Close'})
   end
      
   % ------------------------
      
   function show(who,H,gray)
      % Displays who = 1, 2 or 3.
      x = -4;
      y = 2.5*(2-who);
      for j = 1:length(H)
         pcard(x,y,H(j),gray)
         x = x + 1.5;
      end
      drawnow
   end
      
   % ------------------------
      
   function pcard(x,y,v,gray)
      % pcard(x,y,v) plots v-th card at position (x,y).
      z = exp((0:16)/16*pi/2*i)/16;
      edge = [z+1/2+7*i/8 i*z-1/2+7*i/8 -z-1/2-7*i/8 -i*z+1/2-7*i/8 9/16+7*i/8];
      pips = {'A','2','3','4','5','6','7','8','9','10','J','Q','K'};
      if v <= 0
         % Hole card
         patch(real(edge)+x,imag(edge)+y,[0 0 2/3])
      else
         fs = 20;
         s = ceil(v/13);
         v = mod(v-1,13)+1;
         x1 = x;
         if v==10, x1 = x1-.2; end
         if gray
            offwhite = [.6 .6 .6];
         else
            offwhite = [1 1 1];
         end
         patch(real(edge)+x,imag(edge)+y,offwhite)
         switch s
            case {1,4}, redblack = [0 0 0];
            case {2,3}, redblack = [2/3 0 0];
         end
         text(x1-.2,y,pips{v},'fontname','courier','fontsize',fs, ...
            'fontweight','bold','color',redblack)
         text(x,y+.025,char(166+s),'fontname','symbol','fontsize',fs, ...
            'color',redblack)
      end
   end
      
   % ------------------------
      
   function strat = hard(p,d)
      % Strategy for hands without aces.
      % strategy = hard(player's_total,dealer's_upcard)
      
      % 0 = stand
      % 1 = hit
      % 2 = double down
      
      persistent HARD
      if isempty(HARD)
         x = NaN; % Not possible
         % Dealer shows:
         %      2 3 4 5 6 7 8 9 T A
         HARD = [ ...
            1   x x x x x x x x x x
            2   1 1 1 1 1 1 1 1 1 1
            3   1 1 1 1 1 1 1 1 1 1
            4   1 1 1 1 1 1 1 1 1 1
            5   1 1 1 1 1 1 1 1 1 1
            6   1 1 1 1 1 1 1 1 1 1
            7   1 1 1 1 1 1 1 1 1 1
            8   1 1 1 1 1 1 1 1 1 1
            9   2 2 2 2 2 1 1 1 1 1
           10   2 2 2 2 2 2 2 2 1 1
           11   2 2 2 2 2 2 2 2 2 2
           12   1 1 0 0 0 1 1 1 1 1
           13   0 0 0 0 0 1 1 1 1 1
           14   0 0 0 0 0 1 1 1 1 1
           15   0 0 0 0 0 1 1 1 1 1
           16   0 0 0 0 0 1 1 1 1 1
           17   0 0 0 0 0 0 0 0 0 0
           18   0 0 0 0 0 0 0 0 0 0
           19   0 0 0 0 0 0 0 0 0 0
           20   0 0 0 0 0 0 0 0 0 0];
      end
      strat = HARD(p,d);
   end
      
   % ------------------------
      
   function strat = soft(p,d)
      % Strategy array for hands with aces.
      % strategy = soft(player's_total-11,dealer's_upcard)
      
      % 0 = stand
      % 1 = hit
      % 2 = double down
      
      persistent SOFT
      if isempty(SOFT)
         % Dealer shows:
         %      2 3 4 5 6 7 8 9 T A
         SOFT = [ ...
            1   1 1 1 1 1 1 1 1 1 1
            2   1 1 2 2 2 1 1 1 1 1
            3   1 1 2 2 2 1 1 1 1 1
            4   1 1 2 2 2 1 1 1 1 1
            5   1 1 2 2 2 1 1 1 1 1
            6   2 2 2 2 2 1 1 1 1 1
            7   0 2 2 2 2 0 0 1 1 0
            8   0 0 0 0 0 0 0 0 0 0
            9   0 0 0 0 0 0 0 0 0 0];
      end
      strat = SOFT(p,d);
   end
      
   % ------------------------
      
   function strat = pair(p,d)
      % Strategy for splitting pairs
      % strategy = pair(paired_card,dealer's_upcard)
      
      % 0 = keep pair
      % 1 = split pair
      
      persistent PAIR
      if isempty(PAIR)
         x = NaN; % Not possible
         % Dealer shows:
         %      2 3 4 5 6 7 8 9 T A
         PAIR = [ ...
            1   x x x x x x x x x x
            2   1 1 1 1 1 1 0 0 0 0
            3   1 1 1 1 1 1 0 0 0 0
            4   0 0 0 1 0 0 0 0 0 0
            5   0 0 0 0 0 0 0 0 0 0
            6   1 1 1 1 1 1 0 0 0 0
            7   1 1 1 1 1 1 1 0 0 0
            8   1 1 1 1 1 1 1 1 1 1
            9   1 1 1 1 1 0 1 1 0 0
           10   0 0 0 0 0 0 0 0 0 0
           11   1 1 1 1 1 1 1 1 1 1];
      end
      strat = PAIR(p,d);
   end
end  % blackjack

function S = blackjacksim(n)
%BLACKJACKSIM  Simulate blackjack.
% S = blackjacksim(n)
% Play n hands of blackjack. 
% Returns an n-by-1 vector of cumulative stake.
% See also: blackjack.
      
   S = cumsum(arrayfun(@blackjack_hand,zeros(n,1)));
end
   
% ------------------------
   
function s = blackjack_hand(varargin)
   %BLACKJACK_HAND  Play one hand of blackjack.
   %   s = blackjack_hand returns payoff from one hand.
   
   bet = 10;
   bet1 = bet;
   P = deal;         % Player's hand
   D = deal;         % Dealer's hand
   P = [P deal];
   D = [D -deal];    % Hide dealer's hole card
      
   % Split pairs
   split = (P(1) == P(2));
   if split 
      split = pair(value(P(1)),value(D(1)));
   end
   if split
      P2 = P(2);
      P = [P(1) deal];
      bet2 = bet1;
   end
      
   % Play player's hand(s)
   [P,bet1] = playhand('',P,D,bet1);
   if split
      P2 = [P2 deal];
      [P2,bet2] = playhand('',P2,D,bet2);
   end
      
   % Play dealer's hand
   D(2) = -D(2);     % Reveal dealer's hole card
   while value(D) <= 16
      D = [D deal];
   end
      
   % Payoff
   s = payoff(P,D,split,bet1);
   if split
      s = s + payoff(P2,D,split,bet2);
   end
end
   
% ------------------------
   
function c = deal
   % Simulate continuous shuffling machine with infinite deck.
   % c = deal returns a random integer between 1 and 13.
   c = ceil(13*rand);
end
   
% ------------------------
   
function v = valuehard(X)
   % Evaluate hand
   X = min(X,10);
   v = sum(X);
end
   
% ------------------------
   
function v = value(X)
   % Evaluate hand
   X = min(X,10);
   v = sum(X);
   % Promote soft ace
   if any(X==1) & v<=11
      v = v + 10;
   end
end
   
% ------------------------
   
function [P,bet] = playhand(hand,P,D,bet)
   % Play player's hand
   
   while value(P) < 21
      % 0 = stand
      % 1 = hit
      % 2 = double down
      if any(P==1) & valuehard(P)<=10
         strat = soft(value(P)-11,value(D(1)));
      else
         strat = hard(value(P),value(D(1)));
      end
      if length(P) > 2 & strat == 2
         strat = 1;
      end
      switch strat
          case 0
             break
          case 1
             P = [P deal];
          case 2
             % Double down.
             % Double bet and get one more card
             bet = 2*bet;
             P = [P deal];
             break
          otherwise
             break
      end
   end
end
   
% ------------------------
   
function s = payoff(P,D,split,bet)
   % Payoff
   fs = 20;
   valP = value(P);
   valD = value(D);
   if valP == 21 & length(P) == 2 & ...
      ~(valD == 21 & length(D) == 2) & ~split
      s = 1.5*bet;
   elseif valP > 21
      s = -bet;
   elseif valD > 21
      s = bet;
      str = ['WIN: +' int2str(s)];
   elseif valD > valP
      s = -bet;
   elseif valD < valP
      s = bet;
   else
      s = 0;
   end
end
   
% ------------------------
   
function strat = hard(p,d)
   % Strategy for hands without aces.
   % strategy = hard(player's_total,dealer's_upcard)
   
   % 0 = stand
   % 1 = hit
   % 2 = double down
   
   n = NaN; % Not possible
   % Dealer shows:
   %      2 3 4 5 6 7 8 9 T A
   HARD = [ ...
      1   n n n n n n n n n n
      2   1 1 1 1 1 1 1 1 1 1
      3   1 1 1 1 1 1 1 1 1 1
      4   1 1 1 1 1 1 1 1 1 1
      5   1 1 1 1 1 1 1 1 1 1
      6   1 1 1 1 1 1 1 1 1 1
      7   1 1 1 1 1 1 1 1 1 1
      8   1 1 1 1 1 1 1 1 1 1
      9   2 2 2 2 2 1 1 1 1 1
     10   2 2 2 2 2 2 2 2 1 1
     11   2 2 2 2 2 2 2 2 2 2
     12   1 1 0 0 0 1 1 1 1 1
     13   0 0 0 0 0 1 1 1 1 1
     14   0 0 0 0 0 1 1 1 1 1
     15   0 0 0 0 0 1 1 1 1 1
     16   0 0 0 0 0 1 1 1 1 1
     17   0 0 0 0 0 0 0 0 0 0
     18   0 0 0 0 0 0 0 0 0 0
     19   0 0 0 0 0 0 0 0 0 0
     20   0 0 0 0 0 0 0 0 0 0];
   strat = HARD(p,d);
end
   
% ------------------------
   
function strat = soft(p,d)
   % Strategy array for hands with aces.
   % strategy = soft(player's_total,dealer's_upcard)
   
   % 0 = stand
   % 1 = hit
   % 2 = double down
   
   n = NaN; % Not possible
   % Dealer shows:
   %      2 3 4 5 6 7 8 9 T A
   SOFT = [ ...
      1   n n n n n n n n n n
      2   1 1 2 2 2 1 1 1 1 1
      3   1 1 2 2 2 1 1 1 1 1
      4   1 1 2 2 2 1 1 1 1 1
      5   1 1 2 2 2 1 1 1 1 1
      6   2 2 2 2 2 1 1 1 1 1
      7   0 2 2 2 2 0 0 1 1 0
      8   0 0 0 0 0 0 0 0 0 0
      9   0 0 0 0 0 0 0 0 0 0];
   strat = SOFT(p,d);
end
   
% ------------------------
   
function strat = pair(p,d)
   % Strategy for splitting pairs
   % strategy = pair(paired_card,dealer's_upcard)
   
   % 0 = keep pair
   % 1 = split pair
   
   n = NaN; % Not possible
   % Dealer shows:
   %      2 3 4 5 6 7 8 9 T A
   PAIR = [ ...
      1   n n n n n n n n n n
      2   1 1 1 1 1 1 0 0 0 0
      3   1 1 1 1 1 1 0 0 0 0
      4   0 0 0 1 0 0 0 0 0 0
      5   0 0 0 0 0 0 0 0 0 0
      6   1 1 1 1 1 1 0 0 0 0
      7   1 1 1 1 1 1 1 0 0 0
      8   1 1 1 1 1 1 1 1 1 1
      9   1 1 1 1 1 0 1 1 0 0
     10   0 0 0 0 0 0 0 0 0 0
     11   1 1 1 1 1 1 1 1 1 1];
   strat = PAIR(p,d);
end

Need a fast expert's response?

Submit order

and get a quick answer at the best price

for any assignment or question with DETAILED EXPLANATIONS!

Comments

No comments. Be the first!

Leave a comment

LATEST TUTORIALS
New on Blog
APPROVED BY CLIENTS