From 550b972c7865560dab6b71186dbb4855627f28ed Mon Sep 17 00:00:00 2001 From: Vovanium Date: Mon, 24 Apr 2023 22:40:26 +0300 Subject: [PATCH] * single replace and its example --- alire.toml | 2 +- gpr/examples.gpr | 2 + source/examples/replace.adb | 46 +++++++++++++++++++ .../encodings-generic_single_replace.adb | 18 ++++++-- 4 files changed, 64 insertions(+), 4 deletions(-) create mode 100644 source/examples/replace.adb diff --git a/alire.toml b/alire.toml index 88405b8..6e0dbd2 100644 --- a/alire.toml +++ b/alire.toml @@ -9,4 +9,4 @@ maintainers-logins = ["vovanium"] project-files = ["gpr/encodings.gpr", "gpr/test.gpr", "gpr/examples.gpr"] [[depends-on]] -aunit = "^23.0.0" +aunit = ">=22.0.0" diff --git a/gpr/examples.gpr b/gpr/examples.gpr index 6f95804..27d0179 100644 --- a/gpr/examples.gpr +++ b/gpr/examples.gpr @@ -7,4 +7,6 @@ project Examples extends "common" is package Builder is For Default_Switches("Ada") use Common.Default_Switches; end Builder; + + for Main use ("add_cr", "strip_cr", "replace"); end Examples; \ No newline at end of file diff --git a/source/examples/replace.adb b/source/examples/replace.adb new file mode 100644 index 0000000..4af2fda --- /dev/null +++ b/source/examples/replace.adb @@ -0,0 +1,46 @@ +-- +-- Program reads standard input, replaces string in first parameter +-- with one in second, then writes to standard output +-- + +with Ada.Streams, Ada.Text_IO, Ada.Text_IO.Text_Streams; +use Ada.Streams, Ada.Text_IO, Ada.Text_IO.Text_Streams; +with Ada.Command_Line; +use Ada.Command_Line; +with Encodings.Generic_Single_Replace; +with Encodings.Utility, Encodings.Converters; +use Encodings.Utility, Encodings.Converters; + +procedure Replace is + + Input_Stream : Stream_Access := Stream (Standard_Input); + Output_Stream : Stream_Access := Stream (Standard_Output); + Input_Buffer : String (1 .. 100); + Output_Buffer : String (1 .. 100); + Input_Last, + Input_Read_Last : Natural; + Output_Last : Natural; +begin + if Argument_Count < 2 then + return; + end if; + declare + package Coders is new Encodings.Generic_Single_Replace ( + Character_Type => Character, + String_Type => String, + Original => Argument (1), + Replacement => Argument (2), + Converter_Base => Encodings.Converters.Character_To_Character); + Coder : Coders.Converter; + begin + while not End_Of_File (Standard_Input) loop + Read_String (Input_Stream.all, Input_Buffer, Input_Read_Last); + Input_Last := Input_Buffer'First - 1; + while Input_Last < Input_Read_Last loop + Coder.Process (Input_Buffer (Input_Last + 1 .. Input_Read_Last), + Input_Last, Output_Buffer, Output_Last); + String'Write (Output_Stream, Output_Buffer (Output_Buffer'First .. Output_Last)); + end loop; + end loop; + end; +end Replace; diff --git a/source/library/encodings-generic_single_replace.adb b/source/library/encodings-generic_single_replace.adb index a20ff2c..444442c 100644 --- a/source/library/encodings-generic_single_replace.adb +++ b/source/library/encodings-generic_single_replace.adb @@ -32,8 +32,17 @@ package body Encodings.Generic_Single_Replace is C := Source (Source_Cursor); if C = Original (This.SI) then -- original match if This.SI = Original'Last then -- full string matched - This.TI := Replacement'First - 1; - This.S := Output_Replacement; + case Replacement'Length is + when 0 => + This.SI := Original'First; + when 1 => + Put (Replacement (Replacement'First)); + This.SI := Original'First; + when others => + Put (Replacement (Replacement'First)); + This.TI := Replacement'First; + This.S := Output_Replacement; + end case; else This.SI := This.SI + 1; end if; @@ -41,7 +50,8 @@ package body Encodings.Generic_Single_Replace is if This.SI = Original'First then -- no matched prefix Put (C); else - This.TI := Original'First - 1; + This.TI := Original'First; + Put (Original (Original'First)); This.C := C; This.S := Output_Original; end if; @@ -50,6 +60,7 @@ package body Encodings.Generic_Single_Replace is This.TI := This.TI + 1; if This.TI = This.SI then -- whole matched part already written Put (This.C); + This.SI := Original'First; This.S := Initial; else Put (Original (This.TI)); @@ -58,6 +69,7 @@ package body Encodings.Generic_Single_Replace is This.TI := This.TI + 1; Put (Replacement (This.TI)); if This.TI = Replacement'Last then + This.SI := Original'First; This.S := Initial; end if; end case;