Hi,
I’m trying to develop a hierarchical model with matrix prior structure with PyMC5 and run into errors.
Data:
The input data is a panel data with data points of input features and the output from cross sections over time (illustrated below):
Cross Section, Date, Feature1, Feature2, …Feature 12, Outcome
cross_section1, 2024/1/1, …
cross_section1, 2024/1/2, …
…
cross_section10, 2024/1/1,…
…
cross_section10, 2024/12/1,…
Matrix prior structure
I’d like to do a 2-level linear regression modeling. At the 2nd level, estimate coefficients for each cross section on each feature. At the 1st level, bundle cross sections and features into groups (that are similar) and estimate coefficients for each group of cross sections on each group of features.
My solution (pseudo code) which contains error
with pm.Model() as m:
#level 1
lvl1_coef = pm.Normal(name, mu=np.zeros((num_cs_group, num_feature_group)), tau=np.ones((num_cs_group, num_feature_group))
lvl1_sigma=pm.HalfNormal(name, sigma=np.ones((num_cs_group, num_feature_group)))#level2 lvl2_coef = np.empty((num_cs, num_feature), dtype=object) # maps each level2 coefficient to the corresponding level1 coefficient: for cs in [cs list]: for feature in [feature list]: lvl2_coef[cs, feature] = pm.Normal(name, mu=lvl1_coef[cs_group, feature_group], tau) sigma_y=pm.HalfCauchy('model_error', sigma) # multiply coef of each feature with the feature values and sum across temp = [lvl2_coef[:, feature][cs_index] * stack[feature].values for feature in feature_list] # region_idx, region_codes = pd.factorize(stack["cross section"]) y_hat = pt.sum(temp, axis=0) #pt is pytensor.tensor y_like = pm.Normal('y_like', mu=y_hat, sigma=sigma_y, observed=stack['Outcome'] (ignore intercept for now) trace = pm.sample()
Error Message
it says I get object type in the list after the “temp” step which is not accepted by the pt.sum step that follows it.
Am I moving in the right direction in implementing this matrix prior structure? I know my my approach is very manual without leveraging things like “dims” or “shapes”. My understanding is it’s necessary because of the priors along the feature axis and the customized mapping between the two layers. But would appreciate any simpler implementation approaches. If my implementation is directly correct and necessary, any idea on how to fix the error?
Your thoughts would be much appreciated! Thanks in advance!