Normal-Distribution

理髮師的難題

  • January 6, 2012

我的理髮師 Stacey 總是裝出一副幸福的表情,但經常強調如何管理她的時間。今天斯泰西遲到了我的約會,非常抱歉。理髮時,我想知道:她的標準約會應該多長時間?(如果可以暫時忽略客戶對乾淨整數的偏好)。

需要考慮的是某種“漣漪效應”,一個很晚的客戶可能會導致一連串的預約延遲。實際上,由於害怕這些壓力日,美髮師直覺地學會了將約會的間隔時間越來越長。但是一個最佳的,優雅的解決方案必須由一些統計天才來實現..(如果我們稍微降低現實)

讓我們假設

a) 剪髮時間呈正態分佈,並且

b) 只有一個美髮師。

預約時間過長的成本顯然是浪費了美髮師等待下一次預約的時間。讓我們每分鐘花費 1 美元。

但如果預約時間不夠長,下一位顧客就會一直等待,這對於熱愛顧客的 Stacey 來說是每分鐘 3 美元的成本。

  • Stacey 每天工作長達 8 小時,並且有足夠的需求,她可以滿足盡可能多的約會
  • 平均理髮需要她 30 分鐘,有性病。開發 10 分鐘。(我們還假設男士剪裁和女士剪裁相同!)

編輯 - 有些人正確地指出,Stacey 可以在他們指定的時間之前照顧早期客戶。這增加了另一層複雜性,但如果我們將其視為一個非常現實的問題,我們需要將其包括在內。讓我們忘記我的 90/10 假設,嘗試一個可能更接近現實的假設。

  • 有些顧客遲到,有些顧客早到。顧客的平均遲到 2 分鐘,標準差為 2 分鐘(聽起來很接近現實,不是嗎?)

她的約會到底應該多長時間?


@alexplanation 抱歉,我已將球門柱移到你身上!我相信 R 讀者會欣賞你的回答。

這個問題有很多活動部分,這使得它適合模擬。

首先,正如貓王在評論中提到的那樣,斯泰西似乎應該預約 16 次,因為每次約半小時。但是你知道,隨著約會開始延遲,事情開始變得越來越晚——所以如果 Stacey 只在她還有半個小時的時候才開始約會(掃地的頭髮就這麼多了,嗯,Stacey ?) 如果我們使用水晶球來安排沒有休息時間的約會,那麼我們將有少於 16 個可能的空檔。

最佳間隔理髮

在下一個模擬中,我們可以研究成本曲線作為預約時間的函數。當然,其餘參數最終也會在這裡發揮作用——實際上,Stacey 不會安排她的約會相隔幾分鐘,但這讓我們對正在發生的事情有了一些直覺。

在此處輸入圖像描述

我還繪製了 Stacey 必須作為顏色工作的時間。我決定 Stacey 永遠不會在 7:30 之後安排她的最後一次約會,但有時約會會遲到,或者有延遲!你可以看到她回家的時間是量化的,所以隨著約會的時間變長,你會少一個約會,然後就不必工作到很晚了。而且我認為這是這裡缺少的元素-也許安排您的約會相隔 45 分鐘很好,但是如果您可以將其壓縮到 40 分鐘,您將獲得額外的約會。該成本已包含在 Stacey 的等待中(這就是成本上漲的原因隨著約會時間的延長而增加),但您對 Stacey 等待時間的估計可能不正確。

無論如何,有趣的問題!並且是學習一些 ggplot 優點並記住我的 R 語法非常不穩定的好方法。:)

我的代碼如下 - 請隨時提供改進建議。


要生成頂部圖的代碼:

hairtime = 30
hairsd = 10

nSim = 1000
allCuts = rep(0,nSim)
allTime = rep(0,nSim)

for (i in 1:nSim) {
   t = 0
   ncuts = 0

   while (t < 7.5) {
       ncuts = ncuts+1
       nexthairtime = rnorm(1,hairtime,hairsd)
       t = t+(nexthairtime/60)
   }
   allCuts[i] = ncuts
   allTime[i] = t
}

hist(allCuts,main="Number of haircuts in an 8 hour day",xlab="Customers")


第二次模擬要長很多…

nSim = 100
allCuts = rep(0,nSim)
allTime = rep(0,nSim)

allCost = rep(0,nSim)

lateMean = 10
lateSD = 3

staceyWasted = 1
customerWasted = 3

allLengths = seq(30,60,0.25)

# Keep everything in 'long form' just to make our plotting lives easier later
allApptCosts = data.frame(matrix(ncol=3,nrow=length(allLengths)*nSim))
names(allApptCosts) <- c("Appt.Length","Cost","Time")
ind = 1

# for every appointment length...
for (a in 1:length(allLengths)) {
   apptlen = allLengths[a]
   # ...simulate the time, and the cost of cutting hair.
   for (i in 1:nSim) {
       appts = seq(from=0,to=(8-hairtime/60),by=apptlen/60)
       t = 0
       cost = 0
       ncuts = 0

       for (a in 1:length(appts)) {
           customerArrival = appts[a]
           # late!            
           if (runif(1)>0.9) {
               customerArrival = appts[a]+rnorm(1,lateMean,lateSD)/60
           }

           waitTime = t-customerArrival
           # negative waitTime means the customer arrives late
           cost = cost+max(waitTime,0)*customerWasted+abs(min(waitTime,0))*staceyWasted
                                       # get the haircut
           nexthairtime = rnorm(1,hairtime,hairsd)
           t = customerArrival+(nexthairtime/60)
       }
       allCost[i] = cost
       allApptCosts[ind,1] = apptlen
       allApptCosts[ind,2] = cost
       allApptCosts[ind,3] = t
       ind = ind+1
   }
}

qplot(Appt.Length,Cost,geom=c("point"),alpha=I(0.75),color=Time,data=allApptCosts,xlab="Appointment Length (minutes)",ylab="Cost")+
     geom_smooth(color="black",size=2)+
   opts(axis.title.x=theme_text(size=16))+
   opts(axis.title.y=theme_text(size=16))+
   opts(axis.text.x=theme_text(size=14))+
   opts(axis.text.y=theme_text(size=14))+
   opts(legend.text=theme_text(size=12))+
   opts(legend.title=theme_text(size=12,hjust=-.2))

引用自:https://stats.stackexchange.com/questions/20655

comments powered by Disqus