From 6ec0d18d1033cfc48aa80604181b221309713c5a Mon Sep 17 00:00:00 2001 From: Villu Ruusmann Date: Sun, 28 Mar 2021 11:48:37 +0300 Subject: [PATCH] Added support for the 'FPGrowth' model type. Fixes #50 --- README.md | 1 + .../AssociationRulesModelConverter.java | 36 + .../org/jpmml/sparkml/ItemSetFeature.java | 35 + .../org/jpmml/sparkml/SparkMLEncoder.java | 24 + src/main/java/org/jpmml/sparkml/ZipUtil.java | 7 +- .../sparkml/model/FPGrowthModelConverter.java | 172 + .../META-INF/sparkml2pmml.properties | 1 + .../java/org/jpmml/sparkml/Algorithms.java | 1 + .../jpmml/sparkml/AssociationRulesTest.java | 48 + src/test/java/org/jpmml/sparkml/Datasets.java | 1 + .../org/jpmml/sparkml/SparkMLTestBatch.java | 16 +- src/test/resources/csv/Shopping.csv | 2801 +++++++++++++++++ .../resources/pipeline/FPGrowthShopping.zip | Bin 0 -> 10831 bytes src/test/resources/schema/Shopping.json | 1 + 14 files changed, 3139 insertions(+), 5 deletions(-) create mode 100644 src/main/java/org/jpmml/sparkml/AssociationRulesModelConverter.java create mode 100644 src/main/java/org/jpmml/sparkml/ItemSetFeature.java create mode 100644 src/main/java/org/jpmml/sparkml/model/FPGrowthModelConverter.java create mode 100644 src/test/java/org/jpmml/sparkml/AssociationRulesTest.java create mode 100644 src/test/resources/csv/Shopping.csv create mode 100644 src/test/resources/pipeline/FPGrowthShopping.zip create mode 100644 src/test/resources/schema/Shopping.json diff --git a/README.md b/README.md index ff7ebcab..9bc6f82b 100644 --- a/README.md +++ b/README.md @@ -69,6 +69,7 @@ Java library and command-line application for converting Apache Spark ML pipelin * [`classification.NaiveBayesModel`](https://spark.apache.org/docs/latest/api/java/org/apache/spark/ml/classification/NaiveBayesModel.html) * [`classification.RandomForestClassificationModel`](https://spark.apache.org/docs/latest/api/java/org/apache/spark/ml/classification/RandomForestClassificationModel.html) * [`clustering.KMeansModel`](https://spark.apache.org/docs/latest/api/java/org/apache/spark/ml/clustering/KMeansModel.html) + * [`fpm.FPGrowthModel`](https://spark.apache.org/docs/latest/api/java/org/apache/spark/ml/fpm/FPGrowthModel.html) * [`regression.DecisionTreeRegressionModel`](https://spark.apache.org/docs/latest/api/java/org/apache/spark/ml/regression/DecisionTreeRegressionModel.html) * [`regression.GBTRegressionModel`](https://spark.apache.org/docs/latest/api/java/org/apache/spark/ml/regression/GBTRegressionModel.html) * [`regression.GeneralizedLinearRegressionModel`](https://spark.apache.org/docs/latest/api/java/org/apache/spark/ml/regression/GeneralizedLinearRegressionModel.html) diff --git a/src/main/java/org/jpmml/sparkml/AssociationRulesModelConverter.java b/src/main/java/org/jpmml/sparkml/AssociationRulesModelConverter.java new file mode 100644 index 00000000..e36e5dd8 --- /dev/null +++ b/src/main/java/org/jpmml/sparkml/AssociationRulesModelConverter.java @@ -0,0 +1,36 @@ +/* + * Copyright (c) 2021 Villu Ruusmann + * + * This file is part of JPMML-SparkML + * + * JPMML-SparkML is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * JPMML-SparkML is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with JPMML-SparkML. If not, see . + */ +package org.jpmml.sparkml; + +import org.apache.spark.ml.Model; +import org.apache.spark.ml.param.shared.HasPredictionCol; +import org.dmg.pmml.MiningFunction; + +abstract +public class AssociationRulesModelConverter & HasPredictionCol> extends ModelConverter { + + public AssociationRulesModelConverter(T model){ + super(model); + } + + @Override + public MiningFunction getMiningFunction(){ + return MiningFunction.ASSOCIATION_RULES; + } +} \ No newline at end of file diff --git a/src/main/java/org/jpmml/sparkml/ItemSetFeature.java b/src/main/java/org/jpmml/sparkml/ItemSetFeature.java new file mode 100644 index 00000000..702fdfb4 --- /dev/null +++ b/src/main/java/org/jpmml/sparkml/ItemSetFeature.java @@ -0,0 +1,35 @@ +/* + * Copyright (c) 2021 Villu Ruusmann + * + * This file is part of JPMML-SparkML + * + * JPMML-SparkML is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * JPMML-SparkML is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with JPMML-SparkML. If not, see . + */ +package org.jpmml.sparkml; + +import org.dmg.pmml.Field; +import org.jpmml.converter.ContinuousFeature; +import org.jpmml.converter.Feature; + +public class ItemSetFeature extends Feature { + + public ItemSetFeature(SparkMLEncoder encoder, Field field){ + super(encoder, field.getName(), field.getDataType()); + } + + @Override + public ContinuousFeature toContinuousFeature(){ + throw new UnsupportedOperationException(); + } +} \ No newline at end of file diff --git a/src/main/java/org/jpmml/sparkml/SparkMLEncoder.java b/src/main/java/org/jpmml/sparkml/SparkMLEncoder.java index 46b7027f..1aca47ff 100644 --- a/src/main/java/org/jpmml/sparkml/SparkMLEncoder.java +++ b/src/main/java/org/jpmml/sparkml/SparkMLEncoder.java @@ -34,13 +34,19 @@ import org.dmg.pmml.DataField; import org.dmg.pmml.DataType; import org.dmg.pmml.FieldName; +import org.dmg.pmml.Model; import org.dmg.pmml.OpType; +import org.dmg.pmml.PMML; +import org.dmg.pmml.Visitor; +import org.dmg.pmml.VisitorAction; +import org.dmg.pmml.association.Item; import org.jpmml.converter.BooleanFeature; import org.jpmml.converter.ContinuousFeature; import org.jpmml.converter.Feature; import org.jpmml.converter.ModelEncoder; import org.jpmml.converter.SchemaUtil; import org.jpmml.converter.WildcardFeature; +import org.jpmml.model.visitors.AbstractVisitor; public class SparkMLEncoder extends ModelEncoder { @@ -56,6 +62,24 @@ public SparkMLEncoder(StructType schema, ConverterFactory converterFactory){ setConverterFactory(converterFactory); } + @Override + public PMML encodePMML(Model model){ + PMML pmml = super.encodePMML(model); + + Visitor visitor = new AbstractVisitor(){ + + @Override + public VisitorAction visit(Item item){ + item.setField(null); + + return super.visit(item); + } + }; + visitor.applyTo(pmml); + + return pmml; + } + public boolean hasFeatures(String column){ return this.columnFeatures.containsKey(column); } diff --git a/src/main/java/org/jpmml/sparkml/ZipUtil.java b/src/main/java/org/jpmml/sparkml/ZipUtil.java index fdf6552e..eed436b0 100644 --- a/src/main/java/org/jpmml/sparkml/ZipUtil.java +++ b/src/main/java/org/jpmml/sparkml/ZipUtil.java @@ -56,8 +56,11 @@ public void uncompress(ZipFile zipFile, File dir) throws IOException { File file = new File(dir, entry.getName()); File parentDir = file.getParentFile(); - if(!parentDir.mkdirs()){ - throw new IOException(); + if(!parentDir.exists()){ + + if(!parentDir.mkdirs()){ + throw new IOException(parentDir.getAbsolutePath()); + } } try(OutputStream os = new FileOutputStream(file)){ diff --git a/src/main/java/org/jpmml/sparkml/model/FPGrowthModelConverter.java b/src/main/java/org/jpmml/sparkml/model/FPGrowthModelConverter.java new file mode 100644 index 00000000..7b31438f --- /dev/null +++ b/src/main/java/org/jpmml/sparkml/model/FPGrowthModelConverter.java @@ -0,0 +1,172 @@ +/* + * Copyright (c) 2021 Villu Ruusmann + * + * This file is part of JPMML-SparkML + * + * JPMML-SparkML is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * JPMML-SparkML is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with JPMML-SparkML. If not, see . + */ +package org.jpmml.sparkml.model; + +import java.util.ArrayList; +import java.util.Collections; +import java.util.Comparator; +import java.util.LinkedHashMap; +import java.util.List; +import java.util.Map; + +import org.apache.spark.ml.fpm.FPGrowthModel; +import org.apache.spark.sql.Row; +import org.dmg.pmml.DataField; +import org.dmg.pmml.DataType; +import org.dmg.pmml.FieldName; +import org.dmg.pmml.MiningFunction; +import org.dmg.pmml.MiningSchema; +import org.dmg.pmml.OpType; +import org.dmg.pmml.association.AssociationModel; +import org.dmg.pmml.association.AssociationRule; +import org.dmg.pmml.association.Item; +import org.dmg.pmml.association.ItemRef; +import org.dmg.pmml.association.Itemset; +import org.jpmml.converter.Feature; +import org.jpmml.converter.Schema; +import org.jpmml.converter.SchemaUtil; +import org.jpmml.sparkml.AssociationRulesModelConverter; +import org.jpmml.sparkml.ItemSetFeature; +import org.jpmml.sparkml.SparkMLEncoder; +import scala.collection.JavaConversions; +import scala.collection.Seq; + +public class FPGrowthModelConverter extends AssociationRulesModelConverter { + + public FPGrowthModelConverter(FPGrowthModel model){ + super(model); + } + + @Override + public List getFeatures(SparkMLEncoder encoder){ + FPGrowthModel model = getTransformer(); + + String itemsCol = model.getItemsCol(); + + // Convert from plural to singular + if(itemsCol.endsWith("s")){ + itemsCol = itemsCol.substring(0, itemsCol.length() - 1); + } + + DataField dataField = encoder.createDataField(FieldName.create(itemsCol), OpType.CATEGORICAL, DataType.STRING); + + Feature feature = new ItemSetFeature(encoder, dataField); + + return Collections.singletonList(feature); + } + + @Override + public AssociationModel encodeModel(Schema schema){ + FPGrowthModel model = getTransformer(); + + List features = schema.getFeatures(); + + SchemaUtil.checkSize(1, features); + + Feature feature = features.get(0); + + Map items = new LinkedHashMap<>(); + Map, Itemset> itemsets = new LinkedHashMap<>(); + + List associationRules = new ArrayList<>(); + + List associationRuleRows = (model.associationRules()).collectAsList(); + for(Row associationRuleRow : associationRuleRows){ + List antecedent = JavaConversions.seqAsJavaList((Seq)associationRuleRow.apply(0)); + List consequent = JavaConversions.seqAsJavaList((Seq)associationRuleRow.apply(1)); + + Double confidence = (Double)associationRuleRow.apply(2); + + // XXX + Double lift = 0d; + Double support = 0d; + + Itemset antecedentItemset = ensureItemset(feature, antecedent, itemsets, items); + Itemset consequentItemset = ensureItemset(feature, consequent, itemsets, items); + + AssociationRule associationRule = new AssociationRule() + .setAntecedent(antecedentItemset.getId()) + .setConsequent(consequentItemset.getId()); + + associationRule = associationRule + .setConfidence(confidence) + .setLift(lift) + .setSupport(support); + + associationRules.add(associationRule); + } + + // XXX + int numberOfTransactions = 0; + + MiningSchema miningSchema = new MiningSchema(); + + AssociationModel associationModel = new AssociationModel(MiningFunction.ASSOCIATION_RULES, numberOfTransactions, model.getMinSupport(), model.getMinConfidence(), items.size(), itemsets.size(), associationRules.size(), miningSchema) + .setScorable(Boolean.FALSE); + + (associationModel.getItems()).addAll(items.values()); + (associationModel.getItemsets()).addAll(itemsets.values()); + (associationModel.getAssociationRules()).addAll(associationRules); + + return associationModel; + } + + static + private Itemset ensureItemset(Feature feature, List values, Map, Itemset> itemsets, Map items){ + Itemset itemset = itemsets.get(values); + + if(itemset == null){ + itemset = new Itemset(String.valueOf(itemsets.size() + 1)); + + for(String value : values){ + Item item = items.get(value); + + if(item == null){ + item = new Item(String.valueOf(items.size() + 1), value) + // XXX: See SparkMLEncoder#encodePMML(Model) + .setField(feature.getName()); + + items.put(value, item); + } + + itemset.addItemRefs(new ItemRef(item.getId())); + } + + List itemRefs = itemset.getItemRefs(); + if(itemRefs.size() > 1){ + Comparator comparator = new Comparator(){ + + @Override + public int compare(ItemRef left, ItemRef right){ + int leftId = Integer.parseInt(left.getItemRef()); + int rightId = Integer.parseInt(right.getItemRef()); + + return Integer.compare(leftId, rightId); + } + }; + + Collections.sort(itemRefs, comparator); + } + + itemsets.put(values, itemset); + } + + return itemset; + } +} \ No newline at end of file diff --git a/src/main/resources/META-INF/sparkml2pmml.properties b/src/main/resources/META-INF/sparkml2pmml.properties index f174840b..1a3e67e2 100644 --- a/src/main/resources/META-INF/sparkml2pmml.properties +++ b/src/main/resources/META-INF/sparkml2pmml.properties @@ -36,6 +36,7 @@ org.apache.spark.ml.classification.MultilayerPerceptronClassificationModel = org org.apache.spark.ml.classification.NaiveBayesModel = org.jpmml.sparkml.model.NaiveBayesModelConverter org.apache.spark.ml.classification.RandomForestClassificationModel = org.jpmml.sparkml.model.RandomForestClassificationModelConverter org.apache.spark.ml.clustering.KMeansModel = org.jpmml.sparkml.model.KMeansModelConverter +org.apache.spark.ml.fpm.FPGrowthModel = org.jpmml.sparkml.model.FPGrowthModelConverter org.apache.spark.ml.regression.DecisionTreeRegressionModel = org.jpmml.sparkml.model.DecisionTreeRegressionModelConverter org.apache.spark.ml.regression.GBTRegressionModel = org.jpmml.sparkml.model.GBTRegressionModelConverter org.apache.spark.ml.regression.GeneralizedLinearRegressionModel = org.jpmml.sparkml.model.GeneralizedLinearRegressionModelConverter diff --git a/src/test/java/org/jpmml/sparkml/Algorithms.java b/src/test/java/org/jpmml/sparkml/Algorithms.java index 49ad4622..db16bd6c 100644 --- a/src/test/java/org/jpmml/sparkml/Algorithms.java +++ b/src/test/java/org/jpmml/sparkml/Algorithms.java @@ -21,6 +21,7 @@ interface Algorithms { String DECISION_TREE = "DecisionTree"; + String FP_GROWTH = "FPGrowth"; String GBT = "GBT"; String GLM = "GLM"; String K_MEANS = "KMeans"; diff --git a/src/test/java/org/jpmml/sparkml/AssociationRulesTest.java b/src/test/java/org/jpmml/sparkml/AssociationRulesTest.java new file mode 100644 index 00000000..f05bc776 --- /dev/null +++ b/src/test/java/org/jpmml/sparkml/AssociationRulesTest.java @@ -0,0 +1,48 @@ +/* + * Copyright (c) 2021 Villu Ruusmann + * + * This file is part of JPMML-SparkML + * + * JPMML-SparkML is free software: you can redistribute it and/or modify + * it under the terms of the GNU Affero General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * JPMML-SparkML is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with JPMML-SparkML. If not, see . + */ +package org.jpmml.sparkml; + +import java.util.function.Predicate; + +import com.google.common.base.Equivalence; +import org.dmg.pmml.Model; +import org.dmg.pmml.PMML; +import org.dmg.pmml.association.AssociationModel; +import org.jpmml.evaluator.ResultField; +import org.junit.Test; +import org.spark_project.guava.collect.Iterables; + +import static org.junit.Assert.assertTrue; + +public class AssociationRulesTest extends SparkMLTest implements Algorithms, Datasets { + + @Test + public void evaluateFPGrowthShopping() throws Exception { + Predicate predicate = (resultField -> true); + Equivalence equivalence = getEquivalence(); + + try(SparkMLTestBatch batch = (SparkMLTestBatch)createBatch(FP_GROWTH, SHOPPING, predicate, equivalence)){ + PMML pmml = batch.getPMML(); + + Model model = Iterables.getOnlyElement(pmml.getModels()); + + assertTrue(model instanceof AssociationModel); + } + } +} \ No newline at end of file diff --git a/src/test/java/org/jpmml/sparkml/Datasets.java b/src/test/java/org/jpmml/sparkml/Datasets.java index af937aaa..eb9a094c 100644 --- a/src/test/java/org/jpmml/sparkml/Datasets.java +++ b/src/test/java/org/jpmml/sparkml/Datasets.java @@ -28,6 +28,7 @@ interface Datasets { String HOUSING = "Housing"; String IRIS = "Iris"; String SENTIMENT = "Sentiment"; + String SHOPPING = "Shopping"; String VISIT = "Visit"; FieldName AUDIT_PROBABILITY_TRUE = FieldNameUtil.create("probability", 1); diff --git a/src/test/java/org/jpmml/sparkml/SparkMLTestBatch.java b/src/test/java/org/jpmml/sparkml/SparkMLTestBatch.java index 1476c97b..2e7af2be 100644 --- a/src/test/java/org/jpmml/sparkml/SparkMLTestBatch.java +++ b/src/test/java/org/jpmml/sparkml/SparkMLTestBatch.java @@ -106,9 +106,16 @@ public PMML getPMML() throws Exception { pipelineModel = mlReader.load(tmpPipelineDir.getAbsolutePath()); } - Dataset dataset; + Dataset dataset = null; + dataset: try(InputStream is = open("/csv/" + getDataset() + ".csv")){ + + // XXX + if((Datasets.SHOPPING).equals(getDataset())){ + break dataset; + } + File tmpCsvFile = File.createTempFile(getDataset(), ".csv"); tmpResources.add(tmpCsvFile); @@ -146,8 +153,11 @@ public PMML getPMML() throws Exception { } PMMLBuilder pmmlBuilder = new PMMLBuilder(schema, pipelineModel) - .putOptions(options) - .verify(dataset, precision, zeroThreshold); + .putOptions(options); + + if(dataset != null){ + pmmlBuilder = pmmlBuilder.verify(dataset, precision, zeroThreshold); + } PMML pmml = pmmlBuilder.build(); diff --git a/src/test/resources/csv/Shopping.csv b/src/test/resources/csv/Shopping.csv new file mode 100644 index 00000000..2dc50722 --- /dev/null +++ b/src/test/resources/csv/Shopping.csv @@ -0,0 +1,2801 @@ +transaction,item +10150,softdrink +10150,fruitveg +10236,frozenmeal +10236,beer +10360,fish +10360,cannedveg +10360,beer +10360,frozenmeal +10451,confectionery +10451,frozenmeal +10451,beer +10451,cannedveg +10609,fish +10609,fruitveg +10614,softdrink +10645,fruitveg +10645,frozenmeal +10645,beer +10645,cannedveg +10645,freshmeat +10717,fish +10717,fruitveg +10717,freshmeat +10872,fish +10872,frozenmeal +10872,cannedveg +10872,beer +10902,fruitveg +10902,wine +10915,fruitveg +10915,cannedmeat +10915,fish +10915,dairy +10915,frozenmeal +10944,dairy +10944,frozenmeal +10944,beer +10944,freshmeat +10944,cannedveg +10987,dairy +10987,confectionery +10987,fruitveg +10987,wine +11119,softdrink +11119,fish +11119,confectionery +11220,confectionery +11220,frozenmeal +11220,beer +11220,cannedveg +11230,dairy +11230,fish +11230,confectionery +11241,fish +11241,frozenmeal +11241,beer +11241,freshmeat +11241,fruitveg +11241,cannedveg +11357,fish +11357,beer +11553,confectionery +11565,fish +11565,dairy +11565,cannedveg +11565,wine +11565,freshmeat +11818,freshmeat +11966,dairy +11966,fish +11966,confectionery +11966,fruitveg +12291,confectionery +12291,wine +12312,softdrink +12312,frozenmeal +12312,freshmeat +12547,cannedmeat +12547,frozenmeal +12547,beer +12547,cannedveg +12582,fish +12582,fruitveg +12582,freshmeat +12582,beer +12582,wine +12584,fruitveg +12584,confectionery +12584,beer +12584,wine +12694,confectionery +12694,fruitveg +12782,cannedveg +12782,beer +12800,fruitveg +12938,softdrink +12938,frozenmeal +12938,cannedveg +13325,fish +13325,confectionery +13325,wine +13564,dairy +13722,dairy +13722,fish +13722,freshmeat +13722,beer +13722,fruitveg +13747,beer +13893,cannedmeat +13893,fish +13893,frozenmeal +13893,freshmeat +13893,cannedveg +13903,softdrink +13903,cannedmeat +13903,dairy +13903,fruitveg +13903,freshmeat +13903,cannedveg +14015,confectionery +14015,cannedveg +14107,fish +14107,freshmeat +14301,fish +14301,dairy +14301,confectionery +14301,frozenmeal +14301,beer +14301,cannedveg +14301,freshmeat +14368,cannedmeat +14368,confectionery +14368,wine +14514,softdrink +14514,cannedmeat +14630,frozenmeal +14630,beer +14630,cannedveg +14658,cannedmeat +14658,fish +14658,confectionery +14658,wine +14692,cannedveg +14692,wine +14743,frozenmeal +14743,freshmeat +14743,fruitveg +14743,cannedveg +14743,beer +14743,wine +14743,cannedmeat +14743,dairy +14759,softdrink +14759,dairy +14759,cannedveg +14875,freshmeat +14875,beer +14875,wine +14890,freshmeat +14891,cannedveg +14912,frozenmeal +14912,cannedveg +14912,beer +14912,wine +14996,fish +14996,frozenmeal +14996,freshmeat +14996,confectionery +14996,cannedveg +14996,dairy +15068,beer +15072,frozenmeal +15099,fish +15099,frozenmeal +15099,cannedveg +15099,beer +15099,fruitveg +15109,frozenmeal +15177,confectionery +15306,cannedmeat +15306,frozenmeal +15306,cannedveg +15306,beer +15317,dairy +15590,fish +15590,fruitveg +15590,cannedveg +15629,fish +15629,frozenmeal +15650,fish +15663,beer +15835,fish +15882,frozenmeal +15882,beer +15882,cannedveg +16055,fish +16220,softdrink +16220,frozenmeal +16220,confectionery +16220,cannedveg +16220,beer +16287,softdrink +16287,confectionery +16287,wine +16287,fruitveg +16316,fruitveg +16316,fish +16316,frozenmeal +16316,dairy +16350,freshmeat +16350,fruitveg +17064,beer +17110,cannedmeat +17110,frozenmeal +17110,cannedveg +17110,beer +17133,softdrink +17133,frozenmeal +17133,fruitveg +17133,wine +17201,fish +17201,fruitveg +17201,cannedveg +17201,wine +17375,cannedmeat +17470,fish +17470,confectionery +17470,frozenmeal +17470,beer +17571,frozenmeal +17571,fruitveg +17571,beer +17571,dairy +17747,fish +17809,confectionery +17830,cannedmeat +17830,fish +17830,fruitveg +17830,beer +17864,dairy +17864,fruitveg +17864,fish +17864,confectionery +17864,wine +17939,frozenmeal +18030,cannedmeat +18030,fruitveg +18079,wine +18079,dairy +18126,softdrink +18126,fish +18126,cannedveg +18126,fruitveg +18126,wine +18143,cannedmeat +18143,frozenmeal +18143,fruitveg +18228,cannedveg +18331,fruitveg +18331,frozenmeal +18331,confectionery +18331,wine +18334,frozenmeal +18334,confectionery +18334,wine +18464,cannedveg +18517,fruitveg +18517,frozenmeal +18517,beer +18517,cannedveg +18517,freshmeat +18708,fish +18708,frozenmeal +18708,cannedveg +18708,beer +18708,cannedmeat +18724,beer +18724,dairy +18917,dairy +18917,confectionery +18917,frozenmeal +18917,beer +18917,freshmeat +18917,cannedveg +18920,softdrink +18920,cannedveg +18920,wine +18953,fruitveg +18953,cannedmeat +18953,fish +18953,confectionery +19041,fruitveg +19041,fish +19041,freshmeat +19041,cannedveg +19078,fruitveg +19078,confectionery +19193,softdrink +19193,confectionery +19193,wine +19209,frozenmeal +19209,beer +19209,freshmeat +19209,cannedveg +19209,fruitveg +19211,confectionery +19211,frozenmeal +19211,beer +19211,cannedveg +19519,dairy +19519,confectionery +19519,frozenmeal +19519,beer +19613,cannedmeat +19915,fish +19915,fruitveg +19915,cannedmeat +19999,fish +19999,frozenmeal +19999,fruitveg +19999,cannedveg +20158,fish +20158,cannedmeat +20260,confectionery +20260,cannedveg +20325,dairy +20325,frozenmeal +20325,freshmeat +20325,wine +20362,fish +20362,frozenmeal +20386,dairy +20521,fruitveg +20521,cannedveg +20521,wine +20556,fish +20556,beer +20556,fruitveg +20844,cannedmeat +20849,softdrink +20849,dairy +20849,fish +20849,confectionery +20849,cannedveg +20849,wine +20991,frozenmeal +20991,cannedveg +20991,beer +21187,freshmeat +21187,beer +21347,cannedmeat +21347,frozenmeal +21347,confectionery +21543,softdrink +21543,frozenmeal +21543,cannedveg +21543,wine +21787,fish +21814,cannedmeat +21814,frozenmeal +21814,cannedveg +21814,beer +21875,fish +21875,wine +21875,fruitveg +22316,cannedmeat +22316,softdrink +22316,cannedveg +22316,wine +23037,softdrink +23037,cannedveg +23037,fruitveg +23380,fish +23419,cannedmeat +23419,softdrink +23419,cannedveg +23419,wine +23501,softdrink +23501,fish +23501,confectionery +23501,wine +23682,frozenmeal +23682,beer +23682,cannedveg +23682,wine +23718,fish +23718,frozenmeal +23718,cannedveg +23718,wine +23784,dairy +23845,dairy +23845,beer +24210,frozenmeal +24210,cannedveg +24493,fish +24493,freshmeat +24493,fruitveg +24534,softdrink +24534,confectionery +24534,fruitveg +24566,fish +24566,confectionery +24566,cannedveg +24566,wine +24566,cannedmeat +24651,softdrink +24651,confectionery +24651,wine +24686,dairy +24686,fish +24686,confectionery +24686,beer +24686,wine +24864,fruitveg +24864,frozenmeal +24864,cannedveg +24874,freshmeat +24874,confectionery +24874,fruitveg +24874,wine +24874,dairy +25097,softdrink +25097,cannedmeat +25097,frozenmeal +25097,cannedveg +25256,dairy +25256,confectionery +25256,frozenmeal +25256,freshmeat +25311,fruitveg +25311,freshmeat +25311,wine +25405,fish +25405,cannedmeat +25524,cannedmeat +25524,frozenmeal +25524,cannedveg +25668,confectionery +25668,wine +25765,confectionery +25765,wine +25774,softdrink +25774,cannedmeat +25774,fish +25774,confectionery +25774,freshmeat +25774,cannedveg +25774,wine +26061,fruitveg +26061,cannedmeat +26061,fish +26061,frozenmeal +26061,beer +26061,freshmeat +26061,cannedveg +26130,cannedveg +26130,wine +26291,softdrink +26291,freshmeat +26291,wine +26396,cannedveg +26630,fish +26630,freshmeat +26630,wine +26748,wine +26748,dairy +26885,dairy +26885,frozenmeal +26885,cannedveg +26885,beer +27306,softdrink +27306,fruitveg +27306,confectionery +27306,frozenmeal +27306,beer +27306,cannedveg +27371,fish +27371,frozenmeal +27462,softdrink +27462,beer +27496,confectionery +27496,frozenmeal +27496,beer +27664,cannedmeat +27664,softdrink +27664,dairy +27664,fish +27664,fruitveg +27664,frozenmeal +27673,dairy +27673,frozenmeal +27673,confectionery +27673,beer +27673,wine +27682,fish +27682,confectionery +27682,beer +27694,cannedmeat +27694,softdrink +27694,dairy +27694,frozenmeal +27694,cannedveg +27694,beer +27720,fish +27720,frozenmeal +27766,beer +27766,fruitveg +27890,frozenmeal +27890,freshmeat +28061,confectionery +28061,freshmeat +28061,cannedveg +28061,wine +28081,cannedmeat +28081,fish +28081,confectionery +28081,fruitveg +28081,freshmeat +28081,beer +28110,frozenmeal +28138,fish +28233,fish +28233,confectionery +28233,fruitveg +28233,beer +28233,wine +28268,fish +28268,dairy +28313,fruitveg +28313,confectionery +28313,wine +28314,frozenmeal +28314,confectionery +28314,wine +28427,confectionery +28427,frozenmeal +28427,beer +28427,cannedveg +28498,wine +28528,cannedmeat +28528,confectionery +28528,wine +28597,cannedmeat +28597,frozenmeal +28597,beer +28597,cannedveg +28629,confectionery +28629,beer +28630,cannedmeat +28630,fish +28755,fish +28755,confectionery +28803,fish +28803,frozenmeal +28803,beer +28803,cannedveg +28935,frozenmeal +28935,fruitveg +28959,frozenmeal +28977,softdrink +28977,cannedmeat +28977,frozenmeal +28977,beer +28977,freshmeat +28977,cannedveg +28979,confectionery +28979,cannedveg +28979,wine +28994,cannedmeat +28994,fruitveg +28994,fish +29095,frozenmeal +29095,beer +29095,cannedveg +29095,wine +29107,cannedmeat +29107,frozenmeal +29192,confectionery +29192,freshmeat +29224,cannedmeat +29224,fish +29224,confectionery +29224,fruitveg +29224,beer +29224,wine +29310,softdrink +29310,wine +29316,softdrink +29316,frozenmeal +29316,cannedveg +29316,beer +29343,fruitveg +29343,confectionery +29343,freshmeat +29343,wine +29367,frozenmeal +29483,fruitveg +29524,cannedveg +29640,frozenmeal +29640,cannedveg +29640,wine +29640,cannedmeat +29944,softdrink +29944,fish +29944,fruitveg +29944,frozenmeal +29944,beer +30132,dairy +30132,fruitveg +30132,fish +30132,frozenmeal +30132,cannedveg +30132,beer +30239,softdrink +30239,dairy +30239,fruitveg +30243,cannedveg +30243,frozenmeal +30243,confectionery +30243,freshmeat +30243,beer +30243,wine +30243,cannedmeat +30371,fruitveg +30390,softdrink +30423,softdrink +30423,confectionery +30459,fish +30459,confectionery +30459,cannedveg +30459,wine +30504,fish +30504,freshmeat +30558,fish +30850,fish +30850,fruitveg +30989,confectionery +31011,fish +31011,frozenmeal +31011,cannedveg +31011,beer +31011,wine +31011,fruitveg +31033,dairy +31033,confectionery +31033,wine +31046,cannedmeat +31046,fish +31046,frozenmeal +31046,cannedveg +31046,beer +31046,fruitveg +31083,softdrink +31083,fish +31083,confectionery +31083,cannedveg +31083,freshmeat +31083,fruitveg +31083,wine +31384,cannedveg +31552,dairy +31552,confectionery +31552,fruitveg +31828,fish +31828,cannedmeat +31828,dairy +31921,fruitveg +31921,wine +32083,cannedmeat +32083,dairy +32083,freshmeat +32160,confectionery +32160,frozenmeal +32160,beer +32182,beer +32369,confectionery +32369,cannedveg +32380,cannedveg +32380,fruitveg +32380,wine +32392,fish +32392,fruitveg +32408,beer +32432,confectionery +32432,frozenmeal +32432,freshmeat +32444,dairy +32444,fish +32444,fruitveg +32646,fish +32646,confectionery +32646,frozenmeal +32646,beer +32646,fruitveg +32646,cannedveg +32669,frozenmeal +32669,fruitveg +33167,frozenmeal +33167,beer +33172,confectionery +33172,freshmeat +33173,confectionery +33173,wine +33233,freshmeat +33233,wine +33413,frozenmeal +33413,confectionery +33413,wine +33622,fish +33622,beer +33622,fruitveg +33622,wine +33697,cannedmeat +33697,confectionery +33697,wine +33891,fish +33891,freshmeat +34529,cannedmeat +34529,fish +34529,confectionery +34529,fruitveg +34593,dairy +34593,frozenmeal +34593,wine +34593,cannedmeat +34605,softdrink +34605,cannedmeat +34605,confectionery +34605,cannedveg +34605,wine +34702,fish +34702,fruitveg +34750,cannedmeat +34750,fruitveg +34750,cannedveg +34750,beer +34809,cannedmeat +35197,fish +35197,frozenmeal +35197,beer +35197,wine +35262,fruitveg +35262,cannedveg +35262,beer +35262,wine +35519,frozenmeal +35561,frozenmeal +35561,confectionery +35707,softdrink +35707,fish +35904,softdrink +35904,fish +35904,dairy +35904,confectionery +35904,cannedveg +35904,fruitveg +35904,wine +35979,fish +36040,softdrink +36040,frozenmeal +36040,wine +36190,softdrink +36190,frozenmeal +36190,cannedveg +36190,beer +36191,dairy +36191,fish +36191,frozenmeal +36191,fruitveg +36191,beer +36278,softdrink +36278,frozenmeal +36278,freshmeat +36364,cannedmeat +36364,fish +36405,softdrink +36405,frozenmeal +36405,beer +36857,freshmeat +36863,dairy +36863,confectionery +36863,wine +36927,frozenmeal +36927,confectionery +36927,cannedveg +36927,beer +36951,confectionery +36951,beer +37098,softdrink +37098,freshmeat +37098,fruitveg +37114,fish +37114,confectionery +37114,frozenmeal +37114,beer +37114,cannedveg +37166,fruitveg +37166,fish +37166,beer +37366,cannedmeat +37366,dairy +37366,fish +37366,fruitveg +37523,softdrink +37523,dairy +37523,fish +37523,freshmeat +37523,cannedveg +37523,fruitveg +37523,wine +37567,dairy +37567,frozenmeal +37567,freshmeat +37571,softdrink +37571,freshmeat +37571,cannedveg +37571,wine +37784,cannedmeat +37917,fruitveg +37917,freshmeat +37917,confectionery +37917,wine +37917,freshmeat +37917,wine +37939,softdrink +37939,freshmeat +37939,fruitveg +37939,cannedmeat +38014,softdrink +38014,frozenmeal +38014,freshmeat +38014,cannedveg +38014,cannedmeat +38055,fruitveg +38063,fish +38063,confectionery +38063,fruitveg +38063,wine +38097,fish +38097,frozenmeal +38097,cannedveg +38097,beer +38097,wine +38097,fruitveg +38097,cannedmeat +38360,cannedveg +38477,confectionery +38477,freshmeat +38600,confectionery +38600,wine +38608,freshmeat +38608,beer +38645,cannedmeat +38645,fruitveg +38645,fish +38645,confectionery +38645,beer +38645,wine +38723,softdrink +38723,fish +38723,fruitveg +38723,beer +38765,beer +39042,cannedmeat +39042,confectionery +39042,wine +39077,cannedmeat +39077,freshmeat +39080,fish +39080,cannedveg +39081,softdrink +39081,cannedmeat +39081,frozenmeal +39081,dairy +39081,beer +39081,freshmeat +39081,cannedveg +39081,wine +39221,cannedmeat +39221,freshmeat +39715,fruitveg +39808,freshmeat +39808,confectionery +39808,dairy +39817,beer +39884,wine +39914,dairy +39914,fruitveg +39952,softdrink +39952,frozenmeal +39952,cannedveg +39952,beer +39970,frozenmeal +39970,cannedveg +39970,beer +40090,frozenmeal +40090,cannedveg +40208,cannedmeat +40208,freshmeat +40208,frozenmeal +40208,fruitveg +40282,dairy +40282,confectionery +40282,frozenmeal +40282,wine +40459,dairy +40459,confectionery +40459,wine +40505,confectionery +40505,freshmeat +40505,wine +40505,dairy +40579,confectionery +40579,wine +40659,frozenmeal +40659,beer +40659,cannedveg +40690,softdrink +40690,frozenmeal +40690,cannedveg +40743,dairy +40789,dairy +40789,fish +40789,confectionery +40789,fruitveg +40949,cannedmeat +40949,dairy +40949,frozenmeal +40949,beer +40949,cannedveg +40949,fruitveg +41132,confectionery +41132,cannedveg +41157,softdrink +41157,dairy +41157,frozenmeal +41157,fruitveg +41157,cannedmeat +41792,fish +41792,fruitveg +41805,fish +41805,frozenmeal +41805,confectionery +41805,cannedveg +41805,beer +41841,softdrink +41841,dairy +41841,confectionery +41841,fruitveg +41841,freshmeat +41841,cannedveg +41996,dairy +41996,confectionery +42037,cannedmeat +42056,fish +42056,wine +42163,fruitveg +42167,softdrink +42167,freshmeat +42167,wine +42381,cannedmeat +42381,fish +42381,frozenmeal +42381,cannedveg +42381,beer +42381,wine +42459,softdrink +42459,frozenmeal +42459,confectionery +42459,wine +42459,cannedmeat +42524,softdrink +42524,fish +42524,dairy +42524,freshmeat +42524,fruitveg +42653,softdrink +42689,confectionery +42689,fruitveg +42778,softdrink +42778,frozenmeal +42778,cannedveg +42778,beer +42778,dairy +43044,softdrink +43044,freshmeat +43044,fruitveg +43111,softdrink +43111,dairy +43111,cannedveg +43228,fruitveg +43401,frozenmeal +43401,fruitveg +43401,fish +43401,beer +43401,cannedveg +43550,softdrink +43550,frozenmeal +43550,beer +43550,cannedveg +43557,fruitveg +43800,confectionery +43800,cannedveg +43800,beer +43800,wine +43962,fish +43964,cannedveg +43964,fruitveg +43964,wine +44235,confectionery +44235,beer +44235,wine +44235,dairy +44294,frozenmeal +44294,beer +44294,cannedveg +44294,dairy +44452,cannedmeat +44452,beer +44452,fruitveg +44562,softdrink +44562,frozenmeal +44594,confectionery +44594,wine +44775,fruitveg +44775,fish +44775,beer +44775,wine +44825,fish +44825,confectionery +44825,freshmeat +44887,fruitveg +45019,freshmeat +45102,fish +45102,fruitveg +45102,frozenmeal +45375,cannedmeat +45375,frozenmeal +46054,softdrink +46054,frozenmeal +46054,cannedveg +46054,confectionery +46054,freshmeat +46054,beer +46054,cannedmeat +46071,softdrink +46071,fish +46071,fruitveg +46278,fruitveg +46278,freshmeat +46278,beer +46278,cannedveg +46419,confectionery +46539,cannedmeat +46539,dairy +46539,fish +46539,fruitveg +46686,dairy +46730,fruitveg +46730,cannedmeat +47136,fish +47251,softdrink +47251,fish +47251,fruitveg +47251,confectionery +47251,freshmeat +47251,cannedveg +47251,wine +47330,fruitveg +47330,frozenmeal +47330,confectionery +47330,wine +47341,fish +47341,frozenmeal +47341,confectionery +47341,fruitveg +47343,confectionery +47343,frozenmeal +47343,freshmeat +47343,wine +47441,confectionery +47441,frozenmeal +47441,freshmeat +47489,confectionery +47489,wine +47547,softdrink +47598,fruitveg +47598,confectionery +47598,beer +47598,wine +47638,frozenmeal +47638,cannedveg +47638,beer +47913,dairy +47913,confectionery +47913,wine +47914,fish +47914,freshmeat +47914,wine +47914,confectionery +47923,softdrink +47923,dairy +47923,beer +47923,cannedveg +48749,fish +48783,frozenmeal +48783,cannedveg +48783,beer +48783,fruitveg +48893,confectionery +49085,fish +49085,confectionery +49085,wine +49632,fish +49632,confectionery +49632,cannedveg +49632,cannedmeat +49658,softdrink +49658,confectionery +49658,freshmeat +49658,cannedveg +49769,freshmeat +49861,beer +50064,fruitveg +50064,fish +50064,dairy +50064,frozenmeal +50064,beer +50064,cannedveg +50087,wine +50104,fruitveg +50104,fish +50104,beer +50142,wine +50150,fish +50150,softdrink +50150,fruitveg +50150,wine +50180,softdrink +50180,confectionery +50180,cannedveg +50180,cannedmeat +50258,freshmeat +50324,softdrink +50324,fish +50324,freshmeat +50531,fruitveg +50531,dairy +50531,freshmeat +50551,softdrink +50551,dairy +50551,fruitveg +50551,frozenmeal +50551,cannedveg +50633,confectionery +50645,frozenmeal +50645,freshmeat +50647,cannedveg +50961,beer +51384,fish +51732,frozenmeal +51732,freshmeat +51732,beer +51732,cannedveg +51818,fruitveg +51846,fruitveg +51846,fish +51916,cannedmeat +51916,softdrink +51916,dairy +51916,beer +51939,frozenmeal +51939,beer +51939,cannedveg +51939,wine +51979,frozenmeal +51979,confectionery +51979,beer +51979,cannedveg +51979,cannedmeat +52011,beer +52128,frozenmeal +52128,cannedveg +52359,fish +52359,fruitveg +52359,frozenmeal +52359,wine +52421,fruitveg +52421,softdrink +52421,cannedmeat +52421,fish +52421,frozenmeal +52421,beer +52421,cannedveg +52421,wine +52451,dairy +52451,freshmeat +52451,wine +52530,softdrink +53320,softdrink +53320,fish +53320,cannedmeat +53750,confectionery +53750,wine +53953,softdrink +53953,freshmeat +53953,fruitveg +53959,softdrink +53959,dairy +53959,freshmeat +53959,beer +53959,confectionery +54152,frozenmeal +54152,beer +54152,wine +54172,fish +54172,beer +54172,freshmeat +54180,frozenmeal +54180,freshmeat +54180,cannedveg +54180,beer +54313,softdrink +54313,fruitveg +54313,fish +54313,confectionery +54314,freshmeat +54462,dairy +54462,frozenmeal +54462,beer +54462,cannedveg +54462,wine +54981,cannedmeat +54981,cannedveg +54981,wine +55091,beer +55091,cannedmeat +55295,cannedmeat +55295,dairy +55295,frozenmeal +55295,fruitveg +55418,fruitveg +55550,fruitveg +55550,frozenmeal +55550,wine +55552,fish +55552,fruitveg +55625,softdrink +55625,cannedmeat +55625,confectionery +55625,fruitveg +55625,freshmeat +55625,wine +55629,fish +55652,fish +55652,frozenmeal +55652,cannedveg +55652,fruitveg +55652,beer +55951,wine +55951,confectionery +55992,softdrink +55992,fish +55992,cannedmeat +56034,fruitveg +56034,fish +56034,freshmeat +56034,frozenmeal +56034,cannedveg +56034,beer +56097,confectionery +56097,wine +56220,cannedmeat +56220,freshmeat +56258,softdrink +56258,fruitveg +56258,wine +56452,cannedmeat +56452,fruitveg +56452,confectionery +56452,freshmeat +56677,fruitveg +56851,frozenmeal +56851,beer +56851,cannedveg +56885,softdrink +56885,confectionery +56885,frozenmeal +56885,cannedmeat +56885,beer +56885,cannedveg +56885,freshmeat +57068,dairy +57101,fruitveg +57101,frozenmeal +57102,fish +57102,frozenmeal +57102,beer +57102,cannedveg +57207,confectionery +57207,wine +57207,dairy +57268,softdrink +57268,fruitveg +57268,freshmeat +57582,cannedmeat +57582,dairy +57615,cannedmeat +57615,fruitveg +57615,confectionery +57678,frozenmeal +57762,cannedmeat +57762,fruitveg +57851,confectionery +57851,beer +57851,fruitveg +57851,cannedmeat +57952,cannedveg +57952,wine +57952,confectionery +58144,cannedmeat +58144,frozenmeal +58154,cannedmeat +58188,fish +58188,fruitveg +58188,cannedmeat +58235,confectionery +58235,cannedveg +58235,wine +58341,cannedveg +58341,cannedmeat +58343,dairy +58343,confectionery +58388,softdrink +58388,cannedmeat +58388,beer +58485,fruitveg +58485,confectionery +58485,frozenmeal +58566,softdrink +58566,freshmeat +58768,softdrink +58768,wine +58803,frozenmeal +58803,confectionery +58803,freshmeat +58803,cannedveg +58803,beer +58914,frozenmeal +59071,fish +59071,cannedmeat +59071,beer +59184,freshmeat +59297,cannedmeat +59297,confectionery +59297,beer +59297,cannedveg +59297,wine +59349,softdrink +59349,frozenmeal +59349,beer +59349,cannedveg +59349,fruitveg +59352,fish +59352,confectionery +59352,wine +59389,cannedveg +59439,beer +59439,fruitveg +59480,fruitveg +59480,fish +59480,freshmeat +59480,wine +59480,cannedveg +59480,dairy +59580,dairy +59580,frozenmeal +59580,beer +59580,cannedveg +59580,fruitveg +59590,softdrink +59590,dairy +59590,beer +59590,cannedveg +59590,frozenmeal +59599,beer +59599,frozenmeal +59599,cannedmeat +60073,fish +60073,wine +60153,cannedmeat +60153,wine +60153,beer +60153,freshmeat +60159,frozenmeal +60159,cannedveg +60159,beer +60499,freshmeat +60499,fruitveg +60571,fish +60571,frozenmeal +60755,fruitveg +60755,fish +60820,cannedveg +60890,fish +60890,confectionery +60890,frozenmeal +60890,softdrink +60890,freshmeat +60890,beer +60890,cannedveg +61011,beer +61011,confectionery +61107,fruitveg +61107,dairy +61144,softdrink +61144,fish +61144,fruitveg +61144,dairy +61159,fruitveg +61159,softdrink +61159,cannedmeat +61159,freshmeat +61159,fish +61255,softdrink +61255,dairy +61255,confectionery +61255,wine +61270,wine +61309,cannedmeat +61309,wine +61329,fruitveg +61342,cannedmeat +61342,beer +61342,cannedveg +61618,confectionery +61618,cannedveg +61789,fish +61789,beer +61789,cannedveg +61869,frozenmeal +61869,beer +61869,fruitveg +61869,cannedveg +61869,wine +62022,confectionery +62022,wine +62060,frozenmeal +62060,cannedveg +62060,beer +62175,cannedmeat +62175,fruitveg +62175,fish +62175,frozenmeal +62175,beer +62175,freshmeat +62175,cannedveg +62264,confectionery +62455,fish +62789,fruitveg +62789,frozenmeal +62789,beer +62789,cannedveg +62993,dairy +62995,softdrink +62995,fruitveg +63138,fruitveg +63138,frozenmeal +63138,fish +63368,frozenmeal +63368,fruitveg +63368,beer +63368,cannedveg +63420,fish +63420,dairy +63420,frozenmeal +63420,fruitveg +63452,frozenmeal +63452,cannedveg +63452,beer +63452,cannedmeat +63694,dairy +63694,fruitveg +63694,cannedveg +63779,softdrink +63829,beer +63829,confectionery +63880,fruitveg +63880,cannedmeat +63880,fish +63979,softdrink +63979,cannedmeat +63979,beer +63996,fish +63996,cannedveg +64053,wine +64215,frozenmeal +64215,cannedmeat +64215,cannedveg +64215,beer +64215,fruitveg +64239,softdrink +64239,frozenmeal +64239,cannedveg +64239,beer +64239,wine +64281,dairy +64281,frozenmeal +64281,fish +64281,fruitveg +64281,beer +64281,cannedveg +64281,wine +64561,cannedmeat +64561,softdrink +64596,dairy +64596,fish +64596,freshmeat +64596,beer +64668,frozenmeal +64668,beer +64668,cannedveg +64668,softdrink +64668,cannedmeat +64668,dairy +64752,beer +64752,dairy +64752,cannedveg +64861,frozenmeal +64861,confectionery +64861,beer +64861,dairy +64892,frozenmeal +64892,wine +65006,softdrink +65006,fruitveg +65006,fish +65088,fish +65088,fruitveg +65088,confectionery +65088,freshmeat +65225,dairy +65418,confectionery +65418,wine +65425,dairy +65425,beer +65493,softdrink +65853,dairy +65853,fruitveg +66117,fish +66117,cannedmeat +66191,dairy +66191,frozenmeal +66191,beer +66191,fruitveg +66267,fish +66267,confectionery +66267,freshmeat +66267,fruitveg +66267,beer +66267,dairy +66267,wine +66551,dairy +66551,fish +66618,cannedmeat +66618,fruitveg +66618,freshmeat +66618,cannedveg +66711,dairy +66886,cannedmeat +66886,dairy +66886,fruitveg +66940,fish +66940,softdrink +66940,confectionery +66940,wine +66988,fish +66988,frozenmeal +66988,cannedveg +66988,beer +67063,softdrink +67063,fish +67063,freshmeat +67063,wine +67063,confectionery +67133,frozenmeal +67133,confectionery +67133,cannedveg +67133,wine +67362,confectionery +67362,freshmeat +67455,freshmeat +67455,beer +67697,dairy +67697,frozenmeal +67799,confectionery +67799,frozenmeal +67799,fish +67799,fruitveg +67809,frozenmeal +67809,softdrink +68006,freshmeat +68058,dairy +68058,confectionery +68058,fruitveg +68058,fish +68058,wine +68104,fish +68104,frozenmeal +68104,beer +68104,cannedveg +68119,softdrink +68119,cannedmeat +68119,confectionery +68156,softdrink +68156,beer +68193,fruitveg +68438,confectionery +68438,fruitveg +68489,fish +68489,frozenmeal +68501,fruitveg +68501,fish +68501,freshmeat +68501,softdrink +69110,cannedmeat +69110,fruitveg +69110,fish +69110,frozenmeal +69110,confectionery +69110,cannedveg +69110,beer +69110,wine +69122,cannedmeat +69122,dairy +69372,confectionery +69372,freshmeat +69380,confectionery +69380,wine +69401,cannedmeat +69401,fruitveg +69401,confectionery +69401,wine +69718,softdrink +69718,confectionery +69718,wine +69720,freshmeat +69754,softdrink +69754,dairy +69774,frozenmeal +69774,softdrink +69774,beer +69774,cannedveg +69774,wine +69802,beer +69802,cannedveg +69884,softdrink +69884,confectionery +69934,fish +69965,dairy +69965,fish +69965,beer +69965,fruitveg +70014,cannedveg +70014,wine +70018,confectionery +70018,fruitveg +70018,fish +70018,beer +70018,dairy +70018,frozenmeal +70018,wine +70063,wine +70182,cannedveg +70182,frozenmeal +70206,cannedveg +70206,fruitveg +70336,fruitveg +70336,dairy +70359,fish +70359,fruitveg +70428,softdrink +70428,beer +70428,cannedveg +70428,dairy +70428,wine +70481,softdrink +70481,cannedveg +70481,beer +70481,fish +70858,fish +70858,confectionery +70858,fruitveg +70858,cannedveg +70858,freshmeat +70998,frozenmeal +70998,fish +70998,cannedmeat +70998,dairy +71140,beer +71254,frozenmeal +71254,freshmeat +71276,frozenmeal +71276,beer +71276,cannedveg +71343,cannedveg +71343,beer +71343,frozenmeal +71462,confectionery +71462,freshmeat +71462,wine +71600,fish +71600,cannedveg +71600,beer +71600,frozenmeal +71600,wine +71600,fruitveg +71600,cannedmeat +71604,dairy +71604,fish +71604,beer +71607,dairy +71607,fish +71607,confectionery +71607,fruitveg +71652,frozenmeal +71652,cannedveg +71652,beer +71652,dairy +71690,softdrink +71690,fish +71690,beer +71690,fruitveg +71832,cannedmeat +71832,fish +71887,frozenmeal +71887,confectionery +71887,freshmeat +71887,cannedveg +71887,beer +71887,fish +71887,wine +72200,fruitveg +72200,fish +72200,dairy +72298,beer +72299,softdrink +72299,fish +72299,beer +72299,fruitveg +72454,wine +72454,confectionery +72454,beer +72849,cannedmeat +72849,beer +72849,fruitveg +72900,fruitveg +72900,dairy +72900,fish +72901,beer +72902,softdrink +72902,dairy +72902,confectionery +72902,wine +72979,softdrink +72979,frozenmeal +72979,confectionery +72986,beer +73004,wine +73259,cannedmeat +73259,fruitveg +73383,cannedmeat +73441,cannedmeat +73441,fruitveg +73441,fish +73480,frozenmeal +73480,cannedveg +73480,confectionery +73480,beer +73594,dairy +73630,cannedveg +73630,wine +73630,cannedmeat +73651,fruitveg +73651,freshmeat +73708,fruitveg +73708,softdrink +73708,confectionery +73708,fish +73708,cannedveg +73708,wine +74314,cannedmeat +74314,frozenmeal +74314,fruitveg +74423,beer +74463,frozenmeal +74463,softdrink +74463,cannedveg +74876,confectionery +74876,beer +74876,dairy +75118,cannedmeat +75130,fruitveg +75130,beer +75274,softdrink +75274,fish +75274,fruitveg +75274,cannedveg +75663,cannedmeat +75663,freshmeat +75792,wine +75815,confectionery +75815,frozenmeal +75815,wine +75971,fruitveg +75971,dairy +76095,cannedveg +76095,beer +76095,frozenmeal +76145,cannedmeat +76145,freshmeat +76264,fish +76264,fruitveg +76264,freshmeat +76567,fish +76567,cannedveg +76567,fruitveg +76777,confectionery +76777,wine +76944,confectionery +76944,beer +76944,wine +77218,fish +77218,cannedveg +77218,beer +77218,frozenmeal +77218,fruitveg +77218,wine +77232,fish +77232,fruitveg +77232,dairy +77335,softdrink +77335,confectionery +77335,wine +77419,confectionery +77419,beer +77419,cannedveg +77419,frozenmeal +78030,cannedmeat +78030,wine +78030,confectionery +78113,fruitveg +78113,cannedveg +78113,wine +78139,cannedmeat +78139,fruitveg +78139,cannedveg +78302,cannedveg +78302,fruitveg +78357,frozenmeal +78357,dairy +78363,fruitveg +78363,frozenmeal +78363,cannedveg +78363,beer +78363,wine +78428,softdrink +78428,frozenmeal +78598,wine +78598,confectionery +78626,frozenmeal +78626,freshmeat +78639,fish +78967,frozenmeal +78967,beer +78967,cannedveg +79001,confectionery +79001,wine +79001,fish +79039,dairy +79303,dairy +79303,fruitveg +79303,fish +79305,cannedmeat +79305,wine +79384,fish +79535,cannedmeat +79577,freshmeat +79577,wine +79632,beer +79632,frozenmeal +79632,cannedveg +79875,freshmeat +79890,fish +79890,dairy +80198,beer +80198,wine +80198,confectionery +80297,fish +80297,fruitveg +80306,dairy +80306,frozenmeal +80306,cannedmeat +80306,beer +80306,wine +80438,confectionery +80438,wine +80578,confectionery +80578,beer +80617,fish +80617,softdrink +80728,freshmeat +80728,cannedmeat +80728,frozenmeal +80728,confectionery +80728,cannedveg +80869,wine +80869,cannedmeat +80954,frozenmeal +80954,dairy +80954,cannedveg +80954,beer +81034,freshmeat +81034,cannedveg +81034,beer +81034,frozenmeal +81034,cannedmeat +81487,dairy +81487,frozenmeal +81487,beer +81616,fruitveg +81616,confectionery +81616,cannedmeat +81616,cannedveg +81690,confectionery +81690,wine +81745,dairy +81745,softdrink +81825,dairy +81825,fruitveg +81825,fish +81836,frozenmeal +81836,softdrink +81836,fish +81851,confectionery +81851,fish +81851,dairy +81851,fruitveg +81971,cannedveg +81971,fruitveg +81971,fish +81971,dairy +82096,fruitveg +82096,fish +82096,frozenmeal +82096,confectionery +82096,beer +82096,cannedveg +82173,cannedmeat +82173,fruitveg +82173,fish +82173,beer +82419,freshmeat +82419,beer +82419,cannedveg +82558,softdrink +82558,beer +82558,freshmeat +82558,wine +82753,dairy +82753,fruitveg +82753,confectionery +82753,wine +82753,freshmeat +82796,cannedmeat +82801,wine +82801,frozenmeal +82801,cannedveg +82901,confectionery +82901,wine +83003,softdrink +83071,beer +83071,confectionery +83102,fish +83102,frozenmeal +83102,beer +83102,cannedveg +83127,fish +83127,fruitveg +83338,cannedmeat +83340,softdrink +83340,wine +83340,beer +83439,cannedmeat +83439,fish +83439,confectionery +83439,wine +83500,fish +83500,confectionery +83500,cannedveg +83500,cannedmeat +83536,softdrink +83536,beer +83536,fish +83650,fish +83883,confectionery +83883,wine +84033,wine +84033,freshmeat +84033,cannedveg +84042,cannedmeat +84042,frozenmeal +84042,freshmeat +84042,cannedveg +84042,beer +84092,frozenmeal +84092,dairy +84092,wine +84092,softdrink +84092,fish +84092,fruitveg +84092,confectionery +84148,beer +84148,confectionery +84148,fruitveg +84148,fish +84148,wine +84180,cannedveg +84180,beer +84180,frozenmeal +84497,cannedmeat +84497,wine +84497,confectionery +84605,fruitveg +84756,fish +84756,confectionery +84799,freshmeat +84799,cannedmeat +84902,frozenmeal +84903,fruitveg +84903,softdrink +84903,fish +84903,frozenmeal +84937,beer +84937,fruitveg +85081,fruitveg +85081,confectionery +85081,wine +85081,beer +85182,fruitveg +85182,softdrink +85182,freshmeat +85182,fish +85259,frozenmeal +85259,fruitveg +85259,beer +85348,cannedmeat +85472,dairy +85472,confectionery +85472,fish +85475,wine +85475,fruitveg +85585,confectionery +85585,softdrink +85585,wine +85699,fish +85771,cannedmeat +85771,confectionery +85771,wine +85860,cannedmeat +85860,confectionery +85860,freshmeat +85860,dairy +86044,wine +86044,cannedveg +86044,beer +86044,softdrink +86044,frozenmeal +86217,cannedveg +86217,frozenmeal +86217,beer +86331,beer +86331,frozenmeal +86331,fish +86331,confectionery +86331,cannedveg +86350,frozenmeal +86350,softdrink +86612,freshmeat +86759,cannedveg +86983,fish +86983,fruitveg +86983,freshmeat +86983,confectionery +86983,cannedmeat +86983,wine +87066,dairy +87066,fish +87101,cannedmeat +87101,frozenmeal +87101,confectionery +87101,fruitveg +87101,fish +87151,fish +87151,cannedmeat +87151,dairy +87151,confectionery +87151,frozenmeal +87151,wine +87250,freshmeat +87270,dairy +87270,cannedveg +87270,cannedmeat +87270,wine +87450,fish +87450,frozenmeal +87482,cannedmeat +87482,frozenmeal +87482,wine +87482,fruitveg +87703,cannedmeat +87703,confectionery +87703,fruitveg +87703,fish +87793,fish +87793,confectionery +87793,frozenmeal +87793,wine +87953,fish +87953,cannedmeat +87953,frozenmeal +87975,dairy +87975,fish +88019,fruitveg +88176,dairy +88176,frozenmeal +88176,softdrink +88176,confectionery +88176,wine +88260,cannedveg +88260,dairy +88359,fruitveg +88359,confectionery +88359,freshmeat +88549,softdrink +88549,fish +88549,frozenmeal +88549,fruitveg +88596,softdrink +88596,dairy +88596,confectionery +88596,wine +88812,beer +88886,cannedveg +88972,fruitveg +88972,fish +88972,wine +89041,frozenmeal +89041,beer +89041,cannedveg +89106,confectionery +89106,freshmeat +89106,cannedmeat +89106,wine +89209,wine +89233,freshmeat +89250,wine +89250,freshmeat +89250,cannedmeat +89250,confectionery +89302,fish +89406,fruitveg +89406,beer +89425,cannedveg +89425,fish +89425,fruitveg +89425,beer +89460,confectionery +89460,fruitveg +89460,frozenmeal +89460,cannedveg +89460,beer +89484,beer +89484,cannedveg +89485,frozenmeal +89485,cannedmeat +89559,fish +89559,cannedmeat +89559,freshmeat +89559,fruitveg +89649,fruitveg +89649,confectionery +89649,fish +89872,beer +89958,cannedmeat +89958,fish +89958,frozenmeal +89958,confectionery +89958,dairy +90147,dairy +90165,cannedveg +90264,fruitveg +90264,fish +90360,cannedmeat +90360,frozenmeal +90360,beer +90462,wine +90462,frozenmeal +90462,beer +90462,cannedveg +90462,freshmeat +90562,fish +90562,cannedveg +90562,cannedmeat +90730,softdrink +90730,cannedveg +90730,beer +90730,frozenmeal +90861,confectionery +90861,freshmeat +90861,fruitveg +90911,fruitveg +90911,frozenmeal +90911,freshmeat +91019,wine +91055,softdrink +91055,dairy +91074,cannedveg +91074,frozenmeal +91117,fruitveg +91117,fish +91545,dairy +91913,beer +91913,softdrink +91928,softdrink +91928,fruitveg +91928,confectionery +91928,wine +91928,fish +91928,cannedmeat +91972,wine +91972,fruitveg +91972,fish +91972,frozenmeal +91972,confectionery +91986,freshmeat +91986,cannedveg +92125,cannedveg +92209,freshmeat +92209,dairy +92209,cannedmeat +92227,confectionery +92227,cannedveg +92227,fruitveg +92227,wine +92675,freshmeat +92868,cannedveg +92868,wine +92868,frozenmeal +92883,fruitveg +93037,fish +93037,cannedveg +93037,wine +93162,softdrink +93162,confectionery +93162,fish +93304,frozenmeal +93304,confectionery +93353,wine +93353,confectionery +93353,dairy +93353,cannedveg +93353,cannedmeat +93393,beer +93393,fruitveg +93393,freshmeat +93401,fish +93401,wine +93401,confectionery +93469,fruitveg +93469,frozenmeal +93469,softdrink +93469,fish +93469,cannedmeat +93469,dairy +93469,cannedveg +93527,wine +93527,beer +93669,confectionery +93669,wine +93669,cannedveg +93891,fish +93891,fruitveg +93920,frozenmeal +93920,wine +93920,cannedveg +93920,freshmeat +93920,beer +93963,freshmeat +93974,freshmeat +93974,cannedveg +93974,softdrink +94004,beer +94004,frozenmeal +94004,cannedmeat +94015,wine +94015,fruitveg +94015,confectionery +94015,fish +94105,softdrink +94105,freshmeat +94108,softdrink +94108,wine +94108,dairy +94231,cannedmeat +94231,frozenmeal +94231,confectionery +94341,cannedveg +94341,wine +94341,frozenmeal +94341,beer +94467,softdrink +94467,frozenmeal +94467,beer +94467,cannedveg +94467,fish +94531,freshmeat +94531,frozenmeal +94531,cannedmeat +94685,freshmeat +94685,dairy +94754,confectionery +94754,softdrink +94754,wine +94754,fish +94754,cannedmeat +94754,cannedveg +94790,fish +94790,cannedmeat +94864,wine +95026,confectionery +95026,dairy +95026,fish +95141,wine +95141,confectionery +95141,fruitveg +95354,cannedveg +95354,freshmeat +95354,fish +95354,cannedmeat +95354,beer +95354,frozenmeal +95354,softdrink +95443,fruitveg +95443,wine +95479,wine +95479,cannedmeat +95479,confectionery +95479,cannedveg +95488,fruitveg +95488,dairy +95604,fish +95604,wine +95604,beer +95604,cannedveg +95604,cannedmeat +95604,frozenmeal +95655,softdrink +95655,cannedveg +95655,frozenmeal +95655,fish +95887,cannedveg +95887,frozenmeal +95887,softdrink +95887,beer +95887,cannedmeat +95896,wine +95915,cannedmeat +95915,cannedveg +95915,beer +95915,frozenmeal +95921,fruitveg +95921,wine +95921,confectionery +96076,fish +96076,confectionery +96076,cannedveg +96078,confectionery +96078,fruitveg +96078,cannedveg +96078,frozenmeal +96078,beer +96173,softdrink +96289,beer +96289,fruitveg +96289,frozenmeal +96289,cannedveg +96333,cannedveg +96371,dairy +96512,beer +96512,fruitveg +96512,wine +96512,confectionery +96584,fruitveg +96584,softdrink +96694,frozenmeal +96694,fish +96694,beer +96694,cannedveg +96694,wine +96694,cannedmeat +96881,wine +96881,frozenmeal +96881,beer +96881,cannedveg +96881,cannedmeat +96982,beer +96982,cannedveg +96982,frozenmeal +96982,fruitveg +97148,softdrink +97148,confectionery +97148,wine +97148,beer +97148,cannedveg +97267,fish +97267,confectionery +97287,cannedveg +97287,wine +97287,beer +97287,fish +97287,frozenmeal +97328,dairy +97328,cannedveg +97377,beer +97512,freshmeat +97512,softdrink +97761,fish +97761,fruitveg +97761,cannedveg +97761,wine +97761,confectionery +97967,softdrink +97967,fish +98023,fish +98023,frozenmeal +98181,softdrink +98181,confectionery +98181,dairy +98204,frozenmeal +98204,cannedveg +98204,dairy +98204,beer +98352,frozenmeal +98352,cannedmeat +98352,fish +98383,cannedmeat +98383,confectionery +98383,cannedveg +98383,frozenmeal +98409,confectionery +98409,wine +98626,dairy +98626,cannedveg +98626,fish +98626,confectionery +98635,confectionery +98635,freshmeat +98635,wine +98696,confectionery +98696,wine +98809,fruitveg +98809,fish +98809,confectionery +98809,frozenmeal +98809,wine +98809,beer +98836,wine +98836,cannedveg +98836,fish +98836,confectionery +99025,freshmeat +99046,softdrink +99046,beer +99164,confectionery +99164,dairy +99164,softdrink +99292,freshmeat +99292,softdrink +99292,fish +99292,fruitveg +99347,freshmeat +99347,confectionery +99347,cannedveg +99347,wine +99347,dairy +99387,confectionery +99387,freshmeat +99387,cannedmeat +99410,dairy +99457,freshmeat +99457,fruitveg +99457,cannedveg +99457,fish +99575,frozenmeal +99575,fish +99578,cannedmeat +99578,softdrink +99578,confectionery +99624,fruitveg +99624,softdrink +99624,wine +99849,fruitveg +99849,dairy +100047,fish +100047,cannedveg +100047,fruitveg +100255,wine +100256,beer +100256,cannedveg +100256,frozenmeal +100256,wine +100328,fish +100328,cannedveg +100328,freshmeat +100328,beer +100328,frozenmeal +100393,fish +100393,cannedveg +100393,confectionery +100393,fruitveg +100553,fruitveg +100553,softdrink +100553,cannedveg +100553,wine +100754,fruitveg +100754,cannedveg +100754,fish +100754,frozenmeal +100918,cannedmeat +100918,frozenmeal +100918,beer +100918,cannedveg +101031,beer +101031,cannedveg +101031,frozenmeal +101100,wine +101100,frozenmeal +101100,beer +101100,cannedveg +101414,wine +101544,fruitveg +101544,cannedmeat +101544,frozenmeal +101699,cannedmeat +101699,frozenmeal +101699,dairy +101722,frozenmeal +101722,freshmeat +101722,fish +101784,cannedveg +101784,cannedmeat +102206,cannedveg +102206,fruitveg +102215,beer +102215,cannedveg +102215,frozenmeal +102421,fish +102421,softdrink +102421,cannedmeat +102467,cannedmeat +102467,cannedveg +102467,wine +102467,beer +102645,cannedmeat +102645,cannedveg +102703,cannedmeat +102703,softdrink +102703,freshmeat +102703,fruitveg +102733,fish +102733,fruitveg +102733,confectionery +102887,frozenmeal +102887,fruitveg +102934,wine +102934,fruitveg +102934,confectionery +103087,beer +103087,wine +103087,cannedveg +103087,freshmeat +103087,frozenmeal +103139,wine +103139,freshmeat +103139,cannedveg +103147,cannedveg +103166,dairy +103166,freshmeat +103166,wine +103168,confectionery +103168,beer +103168,fruitveg +103168,cannedveg +103168,softdrink +103168,wine +103316,confectionery +103316,freshmeat +103325,frozenmeal +103385,beer +103385,fish +103385,fruitveg +103385,freshmeat +103385,cannedveg +103385,frozenmeal +103446,cannedmeat +103446,dairy +103462,confectionery +103462,fruitveg +103462,beer +103462,wine +103473,frozenmeal +103473,cannedmeat +103485,beer +103596,softdrink +103596,cannedmeat +103708,fish +103708,wine +103749,fish +103749,dairy +104011,softdrink +104011,wine +104111,confectionery +104111,fish +104111,dairy +104165,wine +104327,cannedveg +104327,wine +104554,cannedveg +104554,fish +104554,beer +104554,frozenmeal +104554,fruitveg +104630,wine +104630,fruitveg +104630,confectionery +104722,cannedveg +104722,frozenmeal +104722,beer +104800,beer +104830,fish +104830,freshmeat +104903,fruitveg +104903,confectionery +104903,wine +104971,softdrink +104971,wine +104971,confectionery +104988,cannedmeat +105007,confectionery +105007,dairy +105007,wine +105095,freshmeat +105095,softdrink +105188,softdrink +105225,fruitveg +105225,confectionery +105225,dairy +105412,beer +105429,frozenmeal +105429,freshmeat +105429,fruitveg +105601,frozenmeal +105601,cannedmeat +105601,cannedveg +105601,beer +105816,dairy +105816,fruitveg +105816,cannedveg +105829,frozenmeal +105829,freshmeat +106004,softdrink +106004,wine +106044,frozenmeal +106044,beer +106044,cannedveg +106044,wine +106044,fish +106044,fruitveg +106122,dairy +106122,wine +106288,cannedveg +106288,confectionery +106290,dairy +106314,cannedveg +106314,cannedmeat +106494,beer +106494,wine +106494,fruitveg +106499,beer +106499,frozenmeal +106499,cannedveg +106522,cannedveg +106522,frozenmeal +106522,beer +106531,frozenmeal +106531,fruitveg +106531,fish +106585,cannedveg +106585,cannedmeat +106585,beer +106649,fish +106649,fruitveg +106649,beer +106654,softdrink +106654,frozenmeal +107080,cannedveg +107314,beer +107314,cannedveg +107314,frozenmeal +107314,wine +107499,wine +107499,softdrink +107505,confectionery +107714,freshmeat +107714,cannedmeat +107714,dairy +107714,fruitveg +107714,softdrink +107728,wine +107728,beer +107728,frozenmeal +107728,freshmeat +107876,beer +107876,wine +107876,fish +108003,fish +108003,cannedveg +108003,wine +108153,confectionery +108153,softdrink +108596,cannedmeat +108596,beer +108601,fish +108601,wine +108718,fish +108718,beer +108739,confectionery +108739,fruitveg +108739,softdrink +108739,wine +108764,beer +108764,fish +108764,wine +108764,frozenmeal +108764,cannedveg +108832,fish +108855,wine +108855,confectionery +108855,softdrink +108855,fish +108855,cannedmeat +109000,wine +109000,cannedveg +109000,softdrink +109000,cannedmeat +109048,fish +109048,cannedveg +109048,wine +109048,fruitveg +109048,beer +109061,freshmeat +109061,wine +109061,confectionery +109132,softdrink +109132,freshmeat +109224,beer +109224,fruitveg +109224,fish +109376,wine +109425,cannedmeat +109425,wine +109504,confectionery +109504,dairy +109504,freshmeat +109530,beer +109530,freshmeat +109551,beer +109551,wine +109672,beer +109672,cannedveg +109672,wine +109672,frozenmeal +109798,frozenmeal +109884,fruitveg +109884,cannedmeat +109884,softdrink +109884,fish +109884,confectionery +109884,frozenmeal diff --git a/src/test/resources/pipeline/FPGrowthShopping.zip b/src/test/resources/pipeline/FPGrowthShopping.zip new file mode 100644 index 0000000000000000000000000000000000000000..19a969584c4d29fc50b70cc65eed222120968045 GIT binary patch literal 10831 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 iL)?$>{GXvs^3Y0$3^H54*)U@3