将 Ord 限制为仅字母

Limiting Ord to letters only

我正在尝试为学校项目创建一个简单的加密方法,想法是通过使用用户输入的数字增加它的 ascii 来更改字符,然后将其替换回去。 所以我的问题是当我这样做时,它有效,但它也包含像 %$! ...ETC。 我想要做的是将 Ord 函数限制为仅字母,例如,如果用户输入数字 100,但字母表中只有 26 个字母,它将不断循环遍历这 26 个字母,直到达到第 100 个。 希望我足够清楚大声笑 这是我到目前为止所拥有的,整个代码的一部分:

Procedure Crypting( Var cryptFile : Text; tempVar2 : String; pNumber: Integer);
Begin
  Writeln('Enter P : ');
  Readln(P);
    Reset( cryptFile );
    For i:= 1 to length(tempVar2) do
            Write(Chr(Ord(tempVar2[i])+P));
End;

您似乎希望实施 Caesar cipher

首先,您需要使用if语句来检查当前字符是否为字母。如果是,你就改造它;如果没有,你保持原样。

其次,仅仅在字符编码上加上P是不够的。虽然它适用于 AP = 3,生成 D,但对于 YP = 3 会发生什么?您需要使用 modular arithmetic 才能得到 Y → Z → A → B.

第三,在编程中,合理构造代码并适当地重构它很重要。目前,您混合输入和转换。你应该把它们分开。如果您创建一个 Caesar 函数,您可以在每次需要执行凯撒密码时使用它。

如果我们还需要同时支持大小写字母,最好使用 case 结构而不是 if .. else if .. else 结构。

综合起来:

function Caesar(const S: string; N: Integer): string; // slow
var
  i: Integer;
begin
  Result := '';
  for i := 1 to Length(S) do
    case S[i] of
      'A'..'Z':
        Result := Result + Chr(Ord('A') + (Ord(S[i]) - Ord('A') + N) mod 26);
      'a'..'z':
        Result := Result + Chr(Ord('a') + (Ord(S[i]) - Ord('a') + N) mod 26);
    else
      Result := Result + S[i];
    end;
end;

此函数有效,但从性能的角度来看并不是最佳的,因为您需要为每次迭代分配堆。最好分配一次结果字符串,然后只填充它:

function Caesar(const S: string; N: Integer): string;
var
  i: Integer;
begin
  SetLength(Result, Length(S));
  for i := 1 to Length(S) do
    case S[i] of
      'A'..'Z':
        Result[i] := Chr(Ord('A') + (Ord(S[i]) - Ord('A') + N) mod 26);
      'a'..'z':
        Result[i] := Chr(Ord('a') + (Ord(S[i]) - Ord('a') + N) mod 26);
    else
      Result[i] := S[i];
    end;
end;

一个完整的例子:

program Project1;

{$APPTYPE CONSOLE}

{$R *.res}

uses
  System.SysUtils;

function Caesar(const S: string; N: Integer): string;
var
  i: Integer;
begin
  SetLength(Result, Length(S));
  for i := 1 to Length(S) do
    case S[i] of
      'A'..'Z':
        Result[i] := Chr(Ord('A') + (Ord(S[i]) - Ord('A') + N) mod 26);
      'a'..'z':
        Result[i] := Chr(Ord('a') + (Ord(S[i]) - Ord('a') + N) mod 26);
    else
      Result[i] := S[i];
    end;
end;

var
  s: string;
  N: Integer;

begin

  Writeln('Please enter a string to transform:');
  Readln(s);
  Writeln('Please enter shift size:');
  Readln(N);
  Writeln;
  Writeln('Result: ', Caesar(s, N));
  Writeln;
  Writeln('Thank you for using this program! Have a nice day!');
  Writeln('Press Return to exit.');
  Readln;

end.

(精确的程序结构取决于您使用的 Pascal 的种类 -- Pascal 有很多种。)

截图: