John1024's helpful answer provides a generic solution that shows how to disambiguate options from operands for all POSIX-like utilities.
In the case at hand, the simplest solution is (works not only in bash
, but also in ksh
and zsh
):
printf '%.0s-' {1..100}
Placing %.0s
before the -
avoids the issue of an initial -
getting mistaken for an option.
Slightly optimized:[1]
printf '%.s-' {1..100}
[1] %.0s
is in practice the most portable form (to be fully portable, you must also avoid the brace expansion, {...}
).
%.s
, the equivalent shorthand form, is supported by bash
, ksh
, and dash
, but not zsh
<= v5.2 - even though it is equally POSIX-compliant : "The precision [the part after .
] shall take the form of a ( '.' ) followed by a decimal digit string; a null digit string is treated as zero."
As a side note: The question originally contained a benign (in Bash) typo that sparked a debate: %0.s
instead of %.0s
: %0.s
should effectively be the same as %.0s
, and for that matter, the same as %.s
and %0.0s
(all effectively request: print a [minimum zero-width] field filled with a zero-length string), but in practice isn't: zsh
<= v5.2 doesn't handle %0.s
correctly (again, due to the .s
part).
Similarly, the GNU printf
external-utility implementation (/usr/bin/printf
), as of GNU coreutils v8.24, reports an error with %0.s
, because it generally doesn't accept a field width of 0
with s
: invalid conversion specification
- this matters for lesser-known shells that don't provide printf
as a builtin. Note that the BSD/OSX implementation does not have this problem.
Both zsh
's (<= v5.2) behavior with %.s
and GNU /usr/bin/printf
's behavior with %0s
are deviations from the POSIX spec that smell like bugs.
This question asks about zsh
's behavior regarding %.s
, and the bug has since been confirmed and reported as fixed via a post-v5.2 commit that has yet to be released as of this writing.