$title Demonstrate the use of numpy.multivariate_normal on stock return data using Transfer (gtmvn,SEQ=143) $onText Use the GAMS Transfer method toDense and setRecords to work with "number only" numpy.array to utilize powerful numpy methods like multivariate_normal to generate samples for a multivariate normal distribution. Historic stock return data is used to build up the covariance and mean data required by numpy.multivariate_normal method. $offText Sets dates 'dates' stocks 'stocks'; Table price(dates<,stocks<) 'daily price' $onDelim $include stockdata.csv $offDelim ; Sets dp(dates) 'all but first date'; Parameters return(dates,stocks) 'daily return' mean(stocks) 'expected daily return' cov(stocks,stocks) 'covariance matrix'; Alias (dates,d), (stocks,s,sp); dp(dates) = ord(dates)>1; return(dp(d),s) = log(price(d,s)) - log(price(d-1,s)); mean(s) = sum(dp, return(dp,s))/card(dp); cov(s,sp) = sum(dp, (return(dp,s) - mean(s))*(return(dp,sp) - mean(sp))) / (card(dp)-1); * 100 samples from the multivariate normal distribution represent 100 days of stock returns $if not set NDAYS $set NDAYS 100 Set ds 'simulated days' / d1*d%NDAYS% /; Parameter mvn(stocks,ds) 'simulated daily stock returns based on a multivariate normal'; embeddedCode Python: import gams.transfer as gt from numpy.random import default_rng nr = default_rng(0) # set static seed to avoid that repeated call produce different random sequences m = gt.Container(gams.db, system_directory=r'%gams.sysDir% '.strip()) cov = m.data["cov"].toDense() mu = m.data["mean"].toDense() mvn = nr.multivariate_normal(mu, cov, size=%NDAYS%, method='cholesky') m.data["mvn"].setRecords(mvn.T) m.write(gams.db, ["mvn"]) endEmbeddedCode mvn display mvn;