你如何检查字符串是否以 Ada 中的另一个字符串结尾?
How do you check if string ends with another string in Ada?
每种流行语言都有针对此问题的规范答案,尽管该答案通常归结为:"Use string.endsWith() from the standard library"。对于 Ada,据我在 the docs for the Fixed String package 中可以找到的,没有 string.endswith 函数。
那么,给定两个固定字符串 A 和 B,如何检查 A 是否以 B 结尾?
declare
A : constant String := "John Johnson";
B : constant String := "son";
begin
if A.Ends_With(B) then -- this doesn't compile
Put_Line ("Yay!");
end if;
end
我的目的是为Ada建立一个标准答案。
嗯,这是一个可能的解决方案:
main.adb
with Ada.Text_IO; use Ada.Text_IO;
with Ada.Strings.Fixed; use Ada.Strings.Fixed;
procedure Main is
A : constant String := "John Johnson";
B : constant String := "son";
begin
if Tail (A, B'Length) = B then
Put_Line ("Yay!");
end if;
end Main;
输出
$ ./main
Yay!
更新 (2)
另一个更新(感谢@Brian Drummond 的评论;评论消失了),再次使用 Tail
。这现在几乎与@Zerte 的答案相同,除了对 Ada.Strings.Fixed
:
的依赖
main.adb
with Ada.Text_IO; use Ada.Text_IO;
with Ada.Strings.Fixed; use Ada.Strings.Fixed;
with Ada.Assertions; use Ada.Assertions;
procedure Main is
function Ends_With (Source, Pattern : String) return Boolean is
begin
return Source'Length >= Pattern'Length and then
Tail (Source, Pattern'Length) = Pattern;
end Ends_With;
begin
Assert (Ends_With ("John Johnson", "son") = True);
Assert (Ends_With ("hi", "longer than hi") = False);
Assert (Ends_With ("" , "" ) = True);
Assert (Ends_With (" " , "" ) = True);
Assert (Ends_With ("" , " " ) = False);
Assert (Ends_With (" " , " " ) = True);
Assert (Ends_With ("n ", "n ") = True);
Assert (Ends_With (" n", "n" ) = True);
Assert (Ends_With ("n" , " n") = False);
Assert (Ends_With (" n", " n") = True);
Put_Line ("All OK.");
end Main;
输出
$ ./main
All OK.
这是一个没有任何显式循环的示例。
with Ada.Assertions; use Ada.Assertions;
with Ada.Text_IO; use Ada.Text_IO;
procedure Main is
function Ends_With(Source : String; Pattern : String) return Boolean is
result : Boolean := False;
begin
if Pattern'Length <= Source'Length then
if Pattern'Length > 0 then
result := Source((Source'Last - Pattern'Length + 1)..Source'Last) = Pattern;
else
result := True;
end if;
end if;
return result;
end Ends_With;
begin
Assert (Ends_With ("John Johnson", "son") = True);
Assert (Ends_With ("" , "" ) = True);
Assert (Ends_With (" " , "" ) = True);
Assert (Ends_With ("" , " " ) = False);
Assert (Ends_With (" " , " " ) = True);
Assert (Ends_With ("" , "n" ) = False);
Assert (Ends_With ("n" , "" ) = True);
Assert (Ends_With ("n ", "n ") = True);
Assert (Ends_With (" n", "n" ) = True);
Assert (Ends_With ("n" , " n") = False);
Assert (Ends_With (" n", " n") = True);
Put_Line("All OK");
end Main;
作为 的稍微简化,这也适用:
function Ends_With (Source, Pattern : String) return Boolean is
begin
if Pattern'Length > Source'Length then
return False;
else
return Source (Source'Last - Pattern'Length + 1 .. Source'Last)
= Pattern;
end if;
end Ends_With;
但是,更好的是(谢谢 Zerte),
function Ends_With (Source, Pattern : String) return Boolean is
(Pattern'Length <= Source'Length and then
Source (Source'Last - Pattern'Length + 1 .. Source'Last) = Pattern);
Simon 的回答略有简化:
function Ends_With (Source, Pattern : String) return Boolean is
begin
return Pattern'Length <= Source'Length
and then Source (Source'Last - Pattern'Length + 1 .. Source'Last) = Pattern;
end Ends_With;
每种流行语言都有针对此问题的规范答案,尽管该答案通常归结为:"Use string.endsWith() from the standard library"。对于 Ada,据我在 the docs for the Fixed String package 中可以找到的,没有 string.endswith 函数。
那么,给定两个固定字符串 A 和 B,如何检查 A 是否以 B 结尾?
declare
A : constant String := "John Johnson";
B : constant String := "son";
begin
if A.Ends_With(B) then -- this doesn't compile
Put_Line ("Yay!");
end if;
end
我的目的是为Ada建立一个标准答案。
嗯,这是一个可能的解决方案:
main.adb
with Ada.Text_IO; use Ada.Text_IO;
with Ada.Strings.Fixed; use Ada.Strings.Fixed;
procedure Main is
A : constant String := "John Johnson";
B : constant String := "son";
begin
if Tail (A, B'Length) = B then
Put_Line ("Yay!");
end if;
end Main;
输出
$ ./main
Yay!
更新 (2)
另一个更新(感谢@Brian Drummond 的评论;评论消失了),再次使用 Tail
。这现在几乎与@Zerte 的答案相同,除了对 Ada.Strings.Fixed
:
main.adb
with Ada.Text_IO; use Ada.Text_IO;
with Ada.Strings.Fixed; use Ada.Strings.Fixed;
with Ada.Assertions; use Ada.Assertions;
procedure Main is
function Ends_With (Source, Pattern : String) return Boolean is
begin
return Source'Length >= Pattern'Length and then
Tail (Source, Pattern'Length) = Pattern;
end Ends_With;
begin
Assert (Ends_With ("John Johnson", "son") = True);
Assert (Ends_With ("hi", "longer than hi") = False);
Assert (Ends_With ("" , "" ) = True);
Assert (Ends_With (" " , "" ) = True);
Assert (Ends_With ("" , " " ) = False);
Assert (Ends_With (" " , " " ) = True);
Assert (Ends_With ("n ", "n ") = True);
Assert (Ends_With (" n", "n" ) = True);
Assert (Ends_With ("n" , " n") = False);
Assert (Ends_With (" n", " n") = True);
Put_Line ("All OK.");
end Main;
输出
$ ./main
All OK.
这是一个没有任何显式循环的示例。
with Ada.Assertions; use Ada.Assertions;
with Ada.Text_IO; use Ada.Text_IO;
procedure Main is
function Ends_With(Source : String; Pattern : String) return Boolean is
result : Boolean := False;
begin
if Pattern'Length <= Source'Length then
if Pattern'Length > 0 then
result := Source((Source'Last - Pattern'Length + 1)..Source'Last) = Pattern;
else
result := True;
end if;
end if;
return result;
end Ends_With;
begin
Assert (Ends_With ("John Johnson", "son") = True);
Assert (Ends_With ("" , "" ) = True);
Assert (Ends_With (" " , "" ) = True);
Assert (Ends_With ("" , " " ) = False);
Assert (Ends_With (" " , " " ) = True);
Assert (Ends_With ("" , "n" ) = False);
Assert (Ends_With ("n" , "" ) = True);
Assert (Ends_With ("n ", "n ") = True);
Assert (Ends_With (" n", "n" ) = True);
Assert (Ends_With ("n" , " n") = False);
Assert (Ends_With (" n", " n") = True);
Put_Line("All OK");
end Main;
作为
function Ends_With (Source, Pattern : String) return Boolean is
begin
if Pattern'Length > Source'Length then
return False;
else
return Source (Source'Last - Pattern'Length + 1 .. Source'Last)
= Pattern;
end if;
end Ends_With;
但是,更好的是(谢谢 Zerte),
function Ends_With (Source, Pattern : String) return Boolean is
(Pattern'Length <= Source'Length and then
Source (Source'Last - Pattern'Length + 1 .. Source'Last) = Pattern);
Simon 的回答略有简化:
function Ends_With (Source, Pattern : String) return Boolean is
begin
return Pattern'Length <= Source'Length
and then Source (Source'Last - Pattern'Length + 1 .. Source'Last) = Pattern;
end Ends_With;