Repeat groups help collect data in scenarios where you are required to ask the same group of questions a number of times in order to collect the same information about multiple people or items. For more information on repeat groups, please take a look at this guide. In this documentation, we will demonstrate different methods of collecting household information, where the same group of questions is asked a number of times in order to collect the same data about multiple household members.
Note: The exported data for repeat groups comes in a variety of formats. Depending on the export format, data within repeat groups can make data analysis difficult. We recommend using repeat groups with care and constructing a collection methodology on the use of repeat data before doing large-scale data collection.
Using a Simple Repeat:
Assuming we want the name, gender, and age of members in a household, the survey sheet in our XLSForm would look something like this:
type | name | label | repeat_count | calculation |
begin repeat | hh_repeat | |||
text | name | What is the name of the household member? | ||
select_one gender | gender | What is the gender of the household member? | ||
integer | age | What is the age of the household member? | ||
end repeat | hh_repeat |
When using ODK Collect
Before this set of questions is asked or asked again, a pop-up window will ask if the user wishes to add (another) family member (i.e. group of questions). The pop-up will ask using the label given in the begin repeat field, in this case, the repeat field label is null as no label was included in the XLSForm:
As long as the user clicks Add Group, he or she can keep entering details for additional household members. As soon as he or she clicks Do Not Add, the survey continues (or, in this case, ends, since there are no additional questions).
Note: If you hit Add Group, some questions in the repeat group are required and decided after the group is added. This means you will have to fill in the extra group of required repeat questions to be able to submit the data.
When using Enketo webforms
In the repeat group section in an Enketo web form, there is a + button below the set of questions in the repeat. If the user wishes to add (another) family member, he/she can click on it. As soon as the user clicks on this button, he/she continues adding additional household members.
Determine the number of repeat group iterations
Instead of an infinite number of repeat group iterations, we can determine how many times the questions in the repeat group will be asked using a repeat_count. In our survey above, where we are collecting the name, gender, and age of members in a household, we will add a question before the repeat group of questions asking how many members the household has. We will also add two new columns: repeat_count and calculation. The repeat_count column will help us specify the number of times the group of questions will be asked. The calculation column, in this case, will help us understand the position in the number of repeats from the first member’s group of questions to the last, which will be discussed further below. Our updated survey sheet will look like this:
type | name | label | repeat_count | calculation |
integer | hh_number | How many members live in this household? | ||
begin repeat | hh_repeat_2 | Repeat Count | ${hh_number} | |
calculate | hh_pos | position(..) | ||
text | name_2 | What is the name of the household member? | ||
select_one gender | gender_2 | What is the gender of the household member? | ||
integer | age_2 | What is the age of the household member? | ||
end repeat | hh_repeat_2 |
We can make the survey look neater and easier to understand by adding a reference label ${hh_pos} in the question label, which will show the calculated member’s position. Our survey sheet will look like this:
type | name | label | repeat_count | calculation |
integer | hh_number | How many members live in this household? | ||
begin repeat | hh_repeat_2 | Repeat Count | ${hh_number} | |
calculate | hh_pos | position(..) | ||
text | name_2 | What is the name of household member # ${hh_pos}? | ||
select_one gender | gender_2 | What is ${name_2}’s gender? | ||
integer | age_2 | How old is ${name_2}? | ||
end repeat | hh_repeat_2 |
Representing zero repeats
By default, the user who is filling out the form will see the questions corresponding to one repeat before getting the option to add more. To represent 0 repeats, there are three options:
- When filling out the form and the simple repeats, the form opens with one repeat group opened and a user can delete the repeat group if there is no data to enter the repeat group.
- When the exact dynamic number of repeats is known ahead of time and it equals zero
- When the exact number of repeats is not known ahead of time, use
relevant
to only prompt the user for repeats if there are some more groups to add
Using Indexed-repeat()
Indexed-repeat is a function that allows you to get information from a specific iteration of a repeat group and use it in either another area of the form or another repeat group. In our example, we will capture names from the hh_repeat_3 repeat group and capture their corresponding age and gender from the otherdetails repeat group. Our updated survey sheet will look like this:
type | name | label | repeat_count | calculation |
begin repeat | hh_repeat_3 | HH Member name | ||
calculate | name_pos | position(..) | ||
text | name_3 | What is the name of household member # ${name_pos}? | ||
end repeat | hh_repeat_3 | |||
begin repeat | otherdetails | HH Member ages | count(${name_3}) | |
calculate | namefromearlier | indexed-repeat(${name_3}, ${hh_repeat_3}, position(..)) | ||
select_one gender | gender_3 | What is ${namefromearlier}’s gender? | ||
integer | age_3 | How old is ${namefromearlier}? | ||
end repeat | otherdetails |
In this example, we will extract the name of a household member from the repeat group hh_repeat_3 using the indexed-repeat() function. The calculate function indexed-repeat(${name_3}, ${hh_repeat_3}, position(..)) extracts the name of the household member coinciding with the position in the repeat groups in ${hh_repeat_3} and ${otherdetails}. The repeat group otherdetails has the repeat count set as count(${name_3}), which is the number of household members collected in the hh_repeat_3 repeat group.
Nested repeat
In this section, we will be adding a repeat group to another repeat group. In our case, we will restructure our example so that we will have two repeats, where the education repeat group is in the household_repeat repeat group.
type | name | label | count_repeat | calculation |
integer | number | How many members stay in this household | ||
begin repeat | household_repeat | ${number} | ||
calculate | cal_pos | position(..) | ||
text | name | Name | ||
integer | age | Age | ||
select_one gender | gender | Gender of # ${name} | ||
decimal | weight | Weight of #${name} | ||
integer | schools | How many schools have you attended | ||
begin repeat | education | ${schools} | ||
calculate | cal_pos1 | position(..) | ||
text | school_name | Name of school #${cal_pos1} | ||
select_one level | ed_level | Enter level of education | ||
end repeat | education | |||
end repeat | household_repeat |