Tuesday, May 24, 2011

Complying with AQS legislation while Minimizing Waste


I recently gave a webinar on how food manufacturers in NZ and Australia can comply with the newly introduce Average Quantity System (AQS) legislation. These (currently optional) guidelines indicate how purveyors of pre-packaged good must verify the amount of product contained in the packages they sell.

The big challenge is to minimise waste while still maintaining a high probability of passing an audit (0.99 say).

As well as covering standard quality techniques such as Gage R&R and Control Charts, I outlined the use of the binomial distribution and the inverse normal distribution to calculate the mean of a process in order to pass an AQS audit with a given probability.

To demonstrate the relationship between reducing variation and minimising waste I produced this animation.

The area under the curve between 470g and 485g is keep constant, while the standard deviation is varied from 20 down to 3.

At each stage the waste, a new mean is calculated and the area under the curve greater than the nominal weight of 500g is calculated.

This shows the waste changing from 86.6% (standard deviation = 20) down to 0.1% (standard deviation = 2).

The R code to generate this is a follows.

library(ggplot2)
library(animation)
make_hists<-function(){ for (i in c(20:3)){ sig = i #the standard deviation prob_pass = 0.99 #the probability we pass inspection Lot_size = 500 nom = 500 #the nominal weight n = 50 #the sample size TD = nom*3/100 #the tolerable deficiency m = qnorm(prob_pass) #the inverse cumulative normal defects = 3 #the number of allowable defects #set up the quadratic to solve for p a = n**2+n*(m**2) b = -2*defects*n-n*(m**2) c = 9 #solve for p p = (-b-sqrt((b**2)-(4*a*c)))/(2*a) #run a smulation over a number of values for mu and find the one that works diff = 100 mu = nom-10 while (diff > 0.01){
a = pnorm((nom - TD - mu)/sig, mean = 0, sd = 1)
b = pnorm((nom- 2*TD - mu)/sig, mean = 0, sd = 1)
delta = a - b
diff = abs(p - delta)
mu = mu + 0.01
}

# generate and plot 10,000 sample from a normal distn with mean mu and standard deviation sig
weight = rnorm(10000, mean = mu, sd = sig)
waste = 100*(1-pnorm(500,mean=mu,sd=sig))
tol = (470dat = data.frame(weight, tol)

#plot the histogram with the target and mean lablled

m<- ggplot(dat, aes(x=weight))+
geom_histogram(binwidth = 0.5, aes(fill = tol, colour = tol))+
geom_vline(xintercept = mu)+
geom_vline(xintercept = nom)+
annotate("text", label = paste("target: ", nom), x = 530, y = 700, hjust=0)+
annotate("text", label = paste("P(pass audit): ", prob_pass), x = 530, y = 650, hjust=0)+
annotate("text", label = paste("mean:", round(mu,1)), x = 530, y = 600, hjust=0)+
annotate("text", label = paste("stand. dev: ", sig), x = 530, y = 550, hjust=0)+
annotate("text", label = paste("waste: ", round(waste,1), "%"), x = 530, y = 500, hjust=0)+
xlim(465, 565)+ scale_colour_manual(values = c("red","blue"))+
opts(legend.position = "none")

print(m)
}
}

# make the animation
saveMovie(make_hists(),interval = 1, width = 580, height = 400)

No comments: