Помощь - Поиск - Пользователи - Календарь
Полная версия: Смесь из литер.
Форум «Всё о Паскале» > Pascal, Object Pascal > Задачи
кзои
Приветствую всех. Я вообще новичок в програмировании и вот в ВУЗЕ мне предложили одну задачу, я парюсь и не могу зделать самое главное. В двух словах дана таблица (кодировочная). Приводить её не буду, потому как получится, что я озадачиваю вас писать эту программу. Скажу только, что символы кодируются двумя цифрами


И далее идёт алгоритм смеси.
1)смесь разбивается на группы по N=<число слов в тексте>
2)выделяются 1-е, 2-е и т.д. символы из каждой группы
3)подряд идущие пробелы и знаки препинания объединяются в один символ


Выглядит всё это примерно так.

Исходный текст
ПРИМЕР СОСТАВЛЕНИЯ СМЕСИ.

Результат шифрования
ПССРОМИСЕМТСЕАИРВ._Л._Е._Н._И._Я._ _.

Результат дешифровки (N=3)
1) ПСС|РОМ|ИСЕ|МТС|ЕАИ|РВ.|_Л.|_Е.|_Н.|_И.|_Я.|_ _.
2) ПРИМЕР_ _ _ _ _
СОСТАВЛЕНИЯ_
СМЕСИ…….
3) ПРИМЕР_СОСТАВЛЕНИЯ_СМЕСИ.

=================================================

А теперь о самой проблемме, я не могу реализовать сам этот алгоритм (слишком мало опыта), в принципе вся эта таблица уже находится в программе. Подскажите пожалуйста, как такое реализовать при кодировании. Заранее огромное спасибо, извините за лемерство.
volvo
кзои, я не понял, ты закодировать это не можешь, или ДЕкодировать?
Если кодировать, то извини, как ты хочешь чтобы тебе помогли, если нет данных...

Если ДЕкодировать, то что именно не выходит? Какой из пунктов, тобой обозначенных?
кзои
Мне нужно закодировать и раскодировать файл. А процесс кодирования указан здесь
volvo
кзои, вот тебе пример реализации самого шифрования/дешифрования...
const
max_word = 255;
delimiter = [#32, ',', '.', '!', ':'];
type
wrd_info = record
start, len: byte;
end;

function encode(s: string; var count: integer): string;
var
words: array[1 .. max_word] of wrd_info;
max, i, j, curr_len: byte;

encoded: string;
begin

count := 0; i := 1;
while i <= length(s) do begin

while (s[i] in delimiter) and (i <= length(s)) do inc(i);

curr_len := 0;
while not (s[i] in delimiter) and (i <= length(s)) do begin
inc(i); inc(curr_len);
end;

if curr_len > 0 then begin
inc(count);
with words[count] do begin
start := i - curr_len;
len := curr_len
end;
end;

end;

max := 0;
for i := 1 to count do
if max < words[i].len then max := words[i].len;

encoded := '';
for j := 1 to max + 1 do
for i := 1 to count do begin
if j <= words[i].len then encoded := encoded + s[words[i].start + j - 1]
else encoded := encoded + s[words[i].start + words[i].len];
end;

encode := encoded;
end;

function decode(s: string; n: integer): string;
var
decoded: string;
i, j: integer;
begin
decoded := '';
for i := 1 to n do begin

j := i;
while j <= length(s) do begin
decoded := decoded + s[j];
inc(j, n)
end;

end;

i := 2;
while i <= length(decoded) do begin
if decoded[pred(i)] = decoded[i] then
delete(decoded, i, 1)
else inc(i)
end;

decode := decoded;
end;


var
s: string;
was_encoded, was_decoded: string;
n: integer;

begin
s := 'Пример составления смеси.';
was_encoded := encode(s, n);
writeln('Зашифровано: ', was_encoded)

was_decoded := decode(was_encoded, n);
writeln('Восстановлено: ', was_decoded);
end.


Дальше сам справишься? Что-то я, если честно, не совсем разобрался, что там с таблицей дальше делать?
кзои
Знаете, чувствую не решить мне проблемму. Вот в файле примерная программа, но на Delphi (кстати кодирует она неправильно, но похоже). Я хотел бы вместо алгоритма который в программе, поставить тот который вы дали, как раз в приложенном файле и реализована таблица кодирования. Помогите please. Очень нужно. Я скоро с ума сойду. wacko.gif
volvo
кзои,
в приведенной тобой программе я не разбирался, легче все написать с нуля, тем более "смесь" уже есть... Ты мне расскажи, сначала символы строки меняются на цифры, или сначала - "смесь", а потом замена по таблице?

+ к этому, немного не понятен такой момент: где хранится информация о количестве слов в незакодированной строке? Это же обязательно знать для дешифрования строки. Тоже пишется в файл?
кзои
Сначала производится смесь, а потом кодирование. Кодирование идёт с использованием оператора CASE я таку понял. С ним же идёт и раскодирование, тоесть сама таблица уак-бы им описывается, а сводится всё к чтению файла и созданию щашифрованного. В общем всё с файлами.
volvo
Повторить вопрос?
Цитата
где хранится информация о количестве слов в незакодированной строке?
кзои
Получается, что нигде. Сначала всё смешивается, потом по таблице меняется на код (2 числа), и файл получается зашифрован, а при дешифровке эта таблица берёт первые два символа и заменяет на букву.
volvo
Проверяй:
const
max_word = 255;
delimiter = [#32, ',', '.', '!', ':'];
type
wrd_info = record
start, len: byte;
end;

function encode(s: string; var count: byte): string;
var
words: array[1 .. max_word] of wrd_info;
max, i, j, curr_len: byte;

encoded: string;
begin

count := 0; i := 1;
while i <= length(s) do begin

while (s[i] in delimiter) and (i <= length(s)) do inc(i);

curr_len := 0;
while not (s[i] in delimiter) and (i <= length(s)) do begin
inc(i); inc(curr_len);
end;

if curr_len > 0 then begin
inc(count);
with words[count] do begin
start := i - curr_len;
len := curr_len
end;
end;

end;

max := 0;
for i := 1 to count do
if max < words[i].len then max := words[i].len;

encoded := '';
for j := 1 to max + 1 do
for i := 1 to count do begin
if j <= words[i].len then encoded := encoded + s[words[i].start + j - 1]
else encoded := encoded + s[words[i].start + words[i].len];
end;

encode := encoded;
end;

function decode(s: string; n: byte): string;
var
decoded: string;
i, j: integer;
begin
decoded := '';
for i := 1 to n do begin

j := i;
while j <= length(s) do begin
decoded := decoded + s[j];
inc(j, n)
end;

end;

i := 2;
while i <= length(decoded) do begin
if decoded[pred(i)] = decoded[i] then
delete(decoded, i, 1)
else inc(i)
end;

decode := decoded;
end;

const
table: array['1' .. '6', '1' .. '8'] of char =
(
('а', 'б', 'в', 'г', 'д', 'е', 'ё', 'ж'),
('з', 'и', 'й', 'к', 'л', 'м', 'н', 'о'),
('п', 'р', 'с', 'т', 'у', 'ф', 'х', 'ц'),
('ч', 'ш', 'щ', 'ъ', 'ы', 'ь', 'э', 'ю'),
('я', '1', '2', '3', '4', '5', '6', '7'),
('8', '9', '0', '.', ',', '!', '?', '-')
);

function get_key(ch: char): string;
var i, j: char;
begin
get_key := ' ';
for i := '1' to '6' do
for j := '1' to '8' do
if table[i, j] = ch then begin
get_key := i + j; exit
end;
end;

function s_deshif(s: string): string;
var
rs: string;
i: integer;
begin
rs := '';

i := 1;
while i <= length(s) do begin
if s[i] = ' ' then begin
rs := rs + ' '; inc(i)
end
else begin
rs := rs + table[s[i], s[i+1]]; inc(i, 2)
end;
end;
s_deshif := rs;
end;

procedure encode_file(s_in, s_out: string);

function s_shif(s: string; n: byte): string;
var
rs: string;
i: integer;
begin
rs := '';
for i := 1 to length(s) do
rs := rs + get_key(s[i]);
rs := chr(n) + rs;
s_shif := rs
end;

var
f_in, f_out: text;
s, was_encoded: string;
n: byte;
begin
assign(f_in, s_in); reset(f_in);
assign(f_out, s_out); rewrite(f_out);
while not seekeof(f_in) do begin
readln(f_in, s);
was_encoded := encode(s, n);
writeln(f_out, s_shif(was_encoded, n))
end;
close(f_out);
close(f_in);
end;

procedure decode_file(s_in, s_out: string);
var
f_in, f_out: text;
s: string;
n: byte;
begin
assign(f_in, s_in); reset(f_in);
assign(f_out, s_out); rewrite(f_out);
while not seekeof(f_in) do begin
readln(f_in, s);
n := byte(s[1]); delete(s, 1, 1);
s := s_deshif(s);
writeln(f_out, decode(s, n));
end;
close(f_in);
close(f_out);
end;


begin
encode_file('before.txt', 'after.txt');
decode_file('after.txt', 'restor.txt');
end.


исходный текст - в "before.txt", зашифрованный - в "after.txt", восстановленный - в "restor.txt" ...
кзои
Вот, что получилось

Текст файла before.txt: Всё, что вы видите это просто текст и ничего особого.
На выходе в файле after.txt:


41131347313422272833344522343216 22331728 15282824 412865 22 3333 161265 34 3434 142865 16 28 281465 2865 64
При расшифровке (текст файла restor.txt): (этот текст сюда не вставится, там досовская кодировка (((((( )
volvo
кзои, а в какой кодировке before.txt?

А символы в Table в какой кодировке? Все должно быть в досовской. У нас, извините, раздел "Паскаль"... Если тебе нужна была работа под Windows (в кодировке Win или Unicode), надо было постить тему в Delphi или в 32-битные компиляторы...

+ к этому: если ты НЕ заметил, то обращаю твое внимание, что в таблице, которую ты же и привел, присутствуют ТОЛЬКО символы верхнего регистра. Я заменил их на символы нижнего... С какой такой радости ты в before.txt печатаешь текст, содержащий ОБА регистра? Естественно, уже кодирование будет неверным... Я не говорю о ДЕкодировании.

Ты задание бы внимательно перечитал, прежде чем браться за него.
кзои
Кодировка была DOS, символы большие. Ну в общем спасибо за помощь.
кзои
Извините за назойливость unsure.gif не могли бы В ы обьяснить значение переменный
curr_len; count; len; Я всё зделал как Вы показали, но не получается ( кодировка DOS а на выходе чушь. Я не знаю что делать. Помогите please
Это текстовая версия — только основной контент. Для просмотра полной версии этой страницы, пожалуйста, нажмите сюда.