Чи є спосіб перерахувати набір, скажімо, 30 випадкових файлів з каталогу за допомогою стандартних команд Linux? (в zsh)
Вище описана тут відповідь не працює для мене ( sortне визнає варіант -R)
Чи є спосіб перерахувати набір, скажімо, 30 випадкових файлів з каталогу за допомогою стандартних команд Linux? (в zsh)
Вище описана тут відповідь не працює для мене ( sortне визнає варіант -R)
Відповіді:
Оскільки ви згадуєте zsh:
rand() REPLY=$RANDOM
print -rl -- *(o+rand[1,30])
Ви можете замінити printна сказати ogg123і *сказати**/*.ogg
Спробуйте підключити lsвихід shuf, наприклад,
$ touch 1 2 3 4 5 6 7 8 9 0
$ ls | shuf -n 5
5
9
0
8
1
-nПрапор визначає , скільки випадкових файли , які ви хочете.
command not found(не встановлено): /
ls .
Це вирішити досить легко за допомогою крихітного шматочка Perl. Виберіть чотири файли навмання з поточного каталогу:
perl -MList::Util=shuffle -e 'print shuffle(`ls`)' | head -n 4
Для використання в виробництві я б хотів використовувати розширений скрипт, який не покладається на lsвихід, може приймати будь-який dir, перевіряє ваші аргументи і т. Д. Зауважте, що сам випадковий вибір є лише парою рядків.
#!/usr/bin/perl
use strict;
use warnings;
use List::Util qw( shuffle );
if ( @ARGV < 2 ) {
die "$0 - List n random files from a directory\n"
. "Usage: perl $0 n dir\n";
}
my $n_random = shift;
my $dir_name = shift;
opendir(my $dh, $dir_name) || die "Can't open directory $dir_name: $!";
# Read in the filenames in the directory, skipping '.' and '..'
my @filenames = grep { !/^[.]{1,2}$/ } readdir($dh);
closedir $dh;
# Handle over-specified input
if ( $n_random > $#filenames ) {
print "WARNING: More values requested ($n_random) than available files ("
. @filenames . ") - truncating list\n";
$n_random = @filenames;
}
# Randomise, extract and print the chosen filenames
foreach my $selected ( (shuffle(@filenames))[0..$n_random-1] ) {
print "$selected\n";
}
shuf) була недостатньою для ОП. Що стосується того, що є, а що не є стандартом Unix - Perl існує скрізь, і це вирішує проблему лаконічно і надійно. Якби я дав це як однолінійний Perl, чи вважали б це "командним рядком"? Чи справді Perl є потужним аргументом проти існування цієї відповіді?
perl -MList::Util=shuffle -e 'print shuffle(ls )' | head -n 4Це більше схоже на те, що ви шукали?
Просте рішення, яке дозволяє уникнути розбору ls, а також працює з пробілами:
shuf -en 30 dir/* | while read file; do
echo $file
done
shuf.
shufне згадується у питанні. Ця відповідь все ще буде корисною для інших користувачів.
Онлайнер, що не використовує нічого, крім Zsh:
files=(*); for x in {1..30}; do i=$((RANDOM % ${#files[@]} + 1)); echo "${files[i]}"; done
Те саме в Bash, де індекси масиву базуються на нулі:
files=(*); for x in {1..30}; do i=$((RANDOM % ${#files[@]})); echo "${files[i]}"; done
Зауважте, що жодна версія не враховує дублікатів.