You could use generated content for the dots... (I learned this from this post)
We create the dot leaders with a ‘:before’ pseudo-element attached to the LI elements. The pseudo-element fills the whole width of the list item with dots and the SPANs are put on top. A white background on the SPANs hides the dots behind them and an ‘overflow: hidden’ on the UL ensures the dots do not extend outside the list: (from this w3.org article)
EDIT: Updated code to allow for nested lists
Markup
<ul class="outer">
<li><a href="#">Introduction</a><span>1</span></li>
<li class="nested">
<ul class="inner">
<li><a href="#">Header 1</a><span>2</span>
</li>
<li><a href="#">Header 2</a><span>2</span>
</li>
</ul>
</li>
<li><a href="#">Header 2</a><span>3</span></li>
</ul>
CSS
ul
{
list-style: none;
padding: 0;
overflow-x: hidden;
}
.outer {
width: 70%;
}
.inner
{
padding-left: 20px;
}
li:not(.nested):before {
float: left;
width: 0;
white-space: nowrap;
content:". . . . . . . . . . . . . . . . . . . . "". . . . . . . . . . . . . . . . . . . . "". . . . . . . . . . . . . . . . . . . . "". . . . . . . . . . . . . . . . . . . . "
}
li a:first-child {
padding-right: 0.33em;
background: white
}
a + span {
float: right;
padding-left: 0.33em;
background: white
}