You are looping over the live tree:
for elem2 in tree.iter(tag='second'):
which you then change while iterating. The 'counter' of the iteration won't be told about the changed number of elements, so when looking at element 0 and removing that element, the iterator then moves on to element number 1. But what was element number 1 is now element number 0.
Capture a list of all the elements first, then loop over that:
for elem2 in tree.findall('.//second'):
.findall()
returns a list of results, which doesn't update as you alter the tree.
Now the iteration won't skip the last element:
>>> print ET.tostring(tree)
<zero>
<First>
<second>
<third-num>1</third-num>
<third-def>object001</third-def>
<third-len>458</third-len>
</second>
</First>
</zero>
This phenomenon is not limited to ElementTree trees; see Loop "Forgets" to Remove Some Items