находя отсутствующие значения в диапазоне с помощью любого языка сценариев - жемчуг, Python или сценарий оболочки

Я застрял в одной проблеме нахождения отсутствующих значений в диапазоне, и диапазон является также переменным для последовательных строк.

вход

673 673 673 676 676 680
2667 2667 2668 2670 2671 2674

вывод должен быть похожим на это

674 675 677 678 679
2669 2672 2673

Это - всего одна часть, и значения строки могут быть больше также при необходимости в каком-либо разъяснении сообщите мне.

7
задан Sinan Ünür 28 April 2010 в 10:54
поделиться

9 ответов

Пример кода с использованием Perl:

#!/usr/bin/perl
use strict;
use warnings;

my @missing;

while(<DATA>) {
    my @data = split (/[ ]/, $_);
    my $i = shift @data;
    foreach (@data) {
        if ($_ != ++$i) {
               push @missing, $i .. $_ - 1;
               $i = $_;
        }
    }
}

print join " ", @missing;

__DATA__
673 673 673 676 676 680
2667 2667 2668 2670 2671 2674

OUTPUT

674 675 677 678 679 2669 2672 2673
2
ответ дан 6 December 2019 в 06:49
поделиться

Ruby:

$stdin.each_line do |line|
  numbers = line.scan(/\d+/).map(&:to_i)
  missing = (numbers.min..numbers.max).to_a - numbers
  puts missing.join " "
end

Версия гольфа (79 символов):

puts $stdin.map{|l|n=l.scan(/\d+/).map(&:to_i);((n.min..n.max).to_a-n).join" "}
1
ответ дан 6 December 2019 в 06:49
поделиться

Модификация решения Marcelo с безопасным освобождением дескриптора файла в случае исключения:

with open('myfile.txt') as f:
    numbers = [int(n) for n in f.readline()[:-1].split(' ')]
all_numbers = set(range(numbers[0], numbers[-1]))
missing = all_numbers - set(numbers)

Это также позволяет избежать использования встроенного имени файла .

0
ответ дан 6 December 2019 в 06:49
поделиться

Оболочка с использованием Bash, sort, uniq & jot (Mac OS X):

numbers="673 673 673 676 676 680"
numbers="2667 2667 2668 2670 2671 2674"
sorted=($(IFS=$'\n' echo "${numbers}" | tr " " '\n' | sort -u ))
low=${sorted[0]}
high=${sorted[@]: -1}
( printf "%s\n" "${sorted[@]}"; jot $((${high} - ${low} + 1)) ${low} ${high} ) | sort | uniq -u
0
ответ дан 6 December 2019 в 06:49
поделиться

В Python:

def report_missing_numbers(f):
    for line in f:
        numbers = [int(n) for n in line.split()]
        all_numbers = set(range(numbers[0], numbers[-1]))
        missing = all_numbers - set(numbers)
        yield missing

Примечание: all_numbers - это немного лжи, поскольку диапазон исключает окончательное число, но поскольку это число гарантированно присутствует в наборе, это не влияет на правильность алгоритма.

Примечание: Я удалил [- 1] из моего исходного ответа, поскольку int (n) не заботится о конечных '\ n '.

6
ответ дан 6 December 2019 в 06:49
поделиться

Python:

for line in open("inputfile.txt"):
    vals = set(map(int, line.split()))
    minv, maxv = min(vals), max(vals)
    missing = [str(v) for v in xrange(minv + 1, maxv) if v not in vals]
    print " ".join(missing)
2
ответ дан 6 December 2019 в 06:49
поделиться

Решение Bash:

cat file_of_numbers| xargs -n2 seq | sort -nu
0
ответ дан 6 December 2019 в 06:49
поделиться

Perl:

use Modern::Perl;

for my $line (<DATA>) {
    chomp $line;
    my @numbers     = split /\s+/, $line;
    my ($min, $max) = (sort { $a <=> $b } @numbers)[0, -1];
    my @missing     = grep { not $_ ~~ @numbers } $min .. $max;
    say join " ", @missing;
}

__DATA__
673 673 673 676 676 680
2667 2667 2668 2670 2671 2674
5
ответ дан 6 December 2019 в 06:49
поделиться

Чистый Bash:

while read -a line ; do
  firstvalue=${line[0]}
  lastvalue=${line[${#line[@]}-1]}
  output=()
  # prepare the output array
  for (( item=firstvalue; item<=lastvalue; item++ )); do
    output[$item]=1
  done
  # unset array elements with an index from the input set
  for item in ${line[@]}; do
    unset  "output[$item]"
  done
  # echo the remaining indices
  echo -e "${!output[@]}"
done < "$infile"
1
ответ дан 6 December 2019 в 06:49
поделиться