字典序

字典序dict.pas

【问题描述】

输入文件中包含几行数据,每行又包含多个正整数。你的任务把这些数据(每行数据看作一个整体)按字典序进行排序。这里的字典序是指,先按每行最左边的数进行排序,若有相同的则比较它们的第二个数,以些类推只到比较出大小。例如下面的数据:

14   38   11   89

27   34

27   12   34

27

92    2    3    1

17    2

按此字典排序后的结果为:

14   38    11   89

17    2

27

27   12    34

27   34

92    2     3    1

【输入格式】dict.in

输入的第一行是一个整数N(1<=N<=10000),表示总共有N行数据要进行排序。

以下N行,每行包括Mi(1<=Mi<=50)个数,最好一个数以-1结束,该数不记入到该行数中。

【输出格式】dict.out

按字典序输出数据,共N行。

【样例输入】

6

14 38 11 89 -1

27 34 -1

27 12 34 -1

27 -1

92 2 3 1 -1

17 2 -1

Readln(str1)

Readln(str2);

【样例输出】

14 38 11 89

17 2

27

27 12 34

27 34

92 2 3 1

【问题分析】

本题就是要求我们按字典排序的方式把多行多个数进行排序,称之为多关键字排序。本题的关键点有:

(1)读入数据的处理

由于每行数的个数不一样,以-1为结束,所以读入处理为:

For I := 1 to n do begin

  Read(x); j := 0;

  While x >=0 do begin

    Inc(j);

    A[I, j] := x;

    Read(x);

  End;

  A[I, 0] := j;    //记录每行有几个数

  Readln;

End;

(2)排序中多关键字的处理

  把每一行当作一个整体来处理,即定义两个变量x,m都是数组:

Procedure qsort(L, R : longint);

Var

  I, j : longint;

  X, m :Arr;

Begin

  I := L; j := R; m := a[(I + j) shr 1];

  Repeat

    While check(a[i],m) do inc(i);

    While check(m, a[j]) do dec(j);

    ……

  Until I > j;

  ……

End;

 

这里定义了一个检查函数,用来判断两个数字按字典序的大小关系。

Function check(x, y : Arr) : boolean;

Var

  I : longint;

  Mark : Boolean;

Begin

  Mark := false;

  For I := 1 to 50 do                 

  //由于每行的元素的个数最多为50个,可以事先把把个数字的值都填充为0

    If x[i] < y[i] then begin mark := true; break;end

    Else x[i] > y[i] then break;

  Check := mark;

End;

(3)输出数据的处理

由于在读入时记录了每行数的个数,在输出的时候就容易处理了。

  For I := 1 to n do begin

    For j := 1 to a[I, 0] do write(a[I, j], ‘ ‘); writeln;

  End;

关于主程序中的定义部分为:

Const maxN = 10000;

Type

  Arr = array[0..50] of longint;

Var

  A : array[1..maxN] of Arr;

  N, I, j, x : longint;

原文地址:https://www.cnblogs.com/ahmasoi/p/3499542.html