宏觀經濟學

Matlab:函式中的While循環

  • November 21, 2020

我是 Matlab 的新手(也是 stackexchange 的新手),我需要為動態宏類學習它。

在函式中使用 while 循環時遇到問題。該函式應該計算一個人需要支付價格 p 的硬幣數量。然而,我的函式只提供了一個向量,顯示我需要哪些硬幣,而不是需要多少。我希望,有人跳進來幫助我擺脫困境。這是我的程式碼:

function[c] = achange(p,coins)
s=size(coins);  
c=zeros(1,s(2)); 

while p>0
   for i=1:s(2) 
   if coins(i) <= p 
       p=p-coins(i); 
       c(i)=c(i)+1; 
   end
   end
end 
end

我對這個問題進行了一些思考,然後想出了以下快速破解方法,這似乎可行。

這是原則上應該使用整數完成工作的程式碼:

function  [exch]=achange(p,coins)
s=size(coins);
c=zeros(1,s(2));
coins=sort(coins,'descend');
it=1:s(2);
isaninteger = @(x)isfinite(x) & x==floor(x);
if p<coins(end)
  return
end
if isaninteger(p)==0
  exch.coins=coins;
  exch.c=inf(1,s(2));
  exch.rest=inf;
  return
elseif any(isaninteger(coins)==0)
  exch.coins=coins;
  exch.c=inf(1,s(2));
  exch.rest=inf;
  return
end
rest=0;
while p>0
   trQ=mod(p,coins)==0;
   idx=it(trQ);
   li=length(idx);
   if isempty(idx)
      rst=1;
      rest=rest+rst;
      p=p-rst;
   elseif li>0 && li<s(2)
     ps=it(trQ)==0;
     idx2=idx;
     idx2(ps)=[];
     for k=1:li
         if p>0
            p=p-coins(idx2(k));
            c(idx2(k))=c(idx2(k))+1;
         end
     end
   elseif li==s(2)
    for k=1:li
        if p>0
           p=p-coins(idx(k));
           c(idx(k))=c(idx(k))+1;
        end
    end
   end
end
exch.coins=coins;
exch.c=c;
exch.rest=rest;
end

至少對於以下範例,它有效:

>> exch=achange(57,[10 25])
exch = 
struct with fields:
 coins: [25 10]
     c: [1 2]
  rest: 12

>> exch.coins*exch.c' + exch.rest
ans =
57

或:

>> exch=achange(51,[10 25])
exch = 
struct with fields:
   coins: [25 10]
       c: [1 2]
    rest: 6

>> exch.coins*exch.c' + exch.rest
ans =
51

最後是我的評論範例:

>> exch=achange(60,[1 2 5 10 20])
exch = 
   struct with fields:
   coins: [20 10 5 2 1]
       c: [1 1 3 4 7]
    rest: 0

>> exch.coins*exch.c'  
ans =
60

如果任何輸入不是整數,我們得到

>> exch=achange(57,[5 .10 25])
exch = 
   struct with fields:
   coins: [25 5 0.1000]
       c: [Inf Inf Inf]
   rest: Inf

或類似的

>> exch=achange(57.8,[5 10 25])
exch = 
  struct with fields:
    coins: [25 10 5]
        c: [Inf Inf Inf]
     rest: Inf

更新 21.11.2020

由於上述程式碼對物種的分配不是最優的,例如,從第一個例子中可以看出,剩餘的數量仍然可以分配給一些硬幣,我提供了一個小的修改,應該會產生更好的結果。

上述範例的剩餘量為 $ 12 $ 表明問題的結構沒有改變,這使我們可以遞歸地解決問題。也就是說,我們應該將 While 循環之後的程式碼行替換為以下 If 構造,以便在必要時呼叫遞歸呼叫。

if any(rest>coins)
  exch2=achange(rest,coins);
  exch.coins=coins;
  exch.c=c+exch2.c;
  exch.rest=exch2.rest;
else
  exch.coins=coins;
  exch.c=c;
  exch.rest=rest;
end   

然後我們可以減少第一個例子的剩餘量 $ 12 $ 到 $ 2 $ ,我們可以看穿

>> exch=achange(57,[10 25])
exch = 
  struct with fields:
    coins: [25 10]
        c: [1 3]
     rest: 2

引用自:https://economics.stackexchange.com/questions/40933