Модераторы: Poseidon, Snowy, bems, MetalFan

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Двумерный массив, выполняется только кусок кода 
:(
    Опции темы
MFSham
Дата 20.10.2005, 21:50 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 220
Регистрация: 28.8.2005
Где: Беларусь, Гродно

Репутация: 1
Всего: 3



По условию прога берет данные из внешнего файла. В моем случае это массив. Вот что я накатал.
Код

program Project1;

{$APPTYPE CONSOLE}

uses
  SysUtils;

var
   i , count : byte;
   str : string;
   mas : array of array of integer;
   f : text;
begin
   AssignFile(f,'data.txt');
   Reset(f);
      count:=0;
      while not eof(f) do
        begin
           readln(f,str);
           if str<>'' then
           inc(count);
        end;
   Close(f);

   setlength(mas,count,count);

   Reset(f);
     count:=1;
      while not eof(f) do
        begin
            readln(f,str);
            for i:=1 to length(str)-1 do
               mas[count,i]:=StrToInt(str[i]);
            inc(count);
        end;
   Close(f);       // <-- уже не выполняется

   writeln(count);
   readln;
end.


После заполнения массива компилятор почему-то переходит в конец кода, таким
образом не выполняя оставшуюся часть кода. В чем тут дело?

--------------------
Без ветра трава неподвижна. Без программ компьютеры бесполезны.
PM MAIL   Вверх
Самурай
Дата 20.10.2005, 22:14 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 64
Регистрация: 20.10.2005
Где: Воронежская облас ть > Семилуки

Репутация: 1
Всего: 1



Код

program Project1;

{$APPTYPE CONSOLE}

uses
  SysUtils;

var
   i , count : byte;
   s: string;
   str : integer;
   mas : array of array of integer;
   f : text;
begin
   AssignFile(f,'C:\test.txt');
   Reset(f);
      count:=0;
      while not eof(f) do
        begin
           readln(f,s);
           if s <> '' then
           inc(count);
        end;
   Close(f);

   setlength(mas,count,count);

   i:=0;
   Reset(f);
     count:=0;
      while not eof(f) do
        begin
            read(f,str);
            mas[count,i]:=str;
            if count = High(mas)
             then
              begin
               inc(i);
               count:=0;
              end
             else
              inc(count);
        end;
   Close(f);   

   for count:=0 to High(mas) do
    begin
     for i:=0 to High(mas) do
      write(mas[count,i], ' ');
     writeln;
    end;
   readln;
end.



Работает. Проверял.
PM MAIL ICQ   Вверх
MFSham
Дата 21.10.2005, 00:05 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 220
Регистрация: 28.8.2005
Где: Беларусь, Гродно

Репутация: 1
Всего: 3



Цитата
Работает. Проверял.

Да, твой алгоритм работает, но :
  • Когда создан динамический массив, то ты считываешь число, и записываешь
    только в первые элементы каждой из строк. В то время как в остальных находятся нули.
  • Т.к. ты считываешь число, то если на вход поступает строка вида 0001010, то
    в итоге ты получишь число 1010, тем самым потеряв первые четыре нуля.
Мне гораздо интереснее узнать почему не работает мой алгоритм, чем работает какой-либо
другой, хотя интересно посмотреть и альтернативу.




--------------------
Без ветра трава неподвижна. Без программ компьютеры бесполезны.
PM MAIL   Вверх
Zero
Дата 21.10.2005, 00:09 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Завсегдатай
Сообщений: 2169
Регистрация: 23.10.2004
Где: Россия, г. Рязань

Репутация: 8
Всего: 24



MFSham ты пишешь, на паскале или делфи???
Ошибки которые я вижу на первый взляд следующие:
У тебя, тут написано как в делфи:
Код

AssignFile(f,'C:\test.txt');

А тут, как в паскале:
Код

Close(f);

В этой часте программы:
Код

begin    
            readln(f,str);    
            for i:=1 to length(str)-1 do    
               mas[count,i]:=StrToInt(str[i]);    
            inc(count);    
        end;

У тебя строка:
Код

mas[count,i]:=StrToInt(str[i]);

Присваевает значение str[i], <кол-во символов в строке> раз, а потом только выполняется инкремент:
Код

inc(count);

Цитата(MFSham @ 20.10.2005, 22:50)
В чем тут дело?

Так стоп, да у тебя вообще смотри вот тут, в первой часте:
Код

AssignFile(f,'data.txt');    
   Reset(f);    
      count:=0;    
      while not eof(f) do    
        .......    
        end;    
   Close(f);

У тебя тут из файла содержащего данные происходит считывание, а потом в этом цикле:
Код

Reset(f);    
     count:=1;    
      while not eof(f) do    
        begin    
            readln(f,str);    
            for i:=1 to length(str)-1 do    
               mas[count,i]:=StrToInt(str[i]);    
            inc(count);    
        end;    
   Close(f);

Ты пытаешся путём открытия в записанные данные переприсвоить значения:
Для этого напиши заместо команды Reset(f) --> ReWrite(f), т.е. создание по томуже пути будет, или др. словами перезапись....
И обрати внимание на замечания сказанные выше...
PM MAIL ICQ   Вверх
Самурай
Дата 21.10.2005, 20:09 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 64
Регистрация: 20.10.2005
Где: Воронежская облас ть > Семилуки

Репутация: 1
Всего: 1



MFSham
Ну если мы пытаемся "убрать" из рассмотрения пустые строки, то нам нужно исследовать строки с рассчетом на то, что там могут оказать между цифрами n пробелов, которые мы должны пропускать. Также у нас могут быть неравные строки (т. е. у нас в одной строке меньше элементов, чем в дургой)... А что мы будет делать, если у нас в строке будут не цифры, а буквы? Если Вы приведете пример самой худшей ситуации, то к нему будет очень просто сделать решение... smile
PM MAIL ICQ   Вверх
Самурай
Дата 21.10.2005, 20:32 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 64
Регистрация: 20.10.2005
Где: Воронежская облас ть > Семилуки

Репутация: 1
Всего: 1



Вот функция, которая подгоняет строку из файла под строку, в которой есть только целые числа и они разделены только одним пробелом.

Код

function TrimStr(s: string): string;
var
 buf: string;
 c: char;
begin
 buf:='';
 while s <> '' do
  begin
   c:=s[1];
   if (c in ['0'..'9']) or ((c = '-') and (s[2] in ['0'..'9'])) or (c = ' ')
    then
     buf:=buf + c;
   Delete(s, 1, 1);
  end;
 while Pos('  ', buf) <> 0 do
  buf:=StringReplace(buf, '  ', ' ', [rfReplaceAll]);
 buf:=Trim(buf);
 Result:=buf;
end;


Если наша строка не является строкой с цифрами, то функция соответсвенно вернет пустую строку.
PM MAIL ICQ   Вверх
Самурай
Дата 21.10.2005, 20:44 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 64
Регистрация: 20.10.2005
Где: Воронежская облас ть > Семилуки

Репутация: 1
Всего: 1



Вот этот код берет любой файл и загоняет все целочисленные значения в массив, согласно строкам, в которых данные числа разположены. Вроде проверял...
Код

function TrimStr(s: string): string;
var
 buf: string;
 c: char;
begin
 buf:='';
 while s <> '' do
  begin
   c:=s[1];
   if (c in ['0'..'9']) or ((c = '-') and (s[2] in ['0'..'9'])) or (c = ' ')
    then
     buf:=buf + c;
   Delete(s, 1, 1);
  end;
 while Pos('  ', buf) <> 0 do
  buf:=StringReplace(buf, '  ', ' ', [rfReplaceAll]);
 buf:=Trim(buf);
 Result:=buf;
end;

function GetInteger(var s: string; var i: integer): boolean;
var
 buf:string;
begin
 if Pos(' ', s) <> 0
  then
   begin
    buf:=Copy(s, 1, Pos(' ', s) - 1);
    Delete(s, 1, Pos(' ', s));
   end
  else
   begin
    buf:=s;
    s:='';
   end;
 Result:=buf <> '';
 if Result
  then
   i:=StrToInt(buf);
end;

procedure TForm1.Button1Click(Sender: TObject);
var
 f: TextFile;
 buf: string;
 int: integer;
 m: array of array of integer;
begin
 AssignFile(f, 'C:\test.txt');
 reset(f);
 while not Eof(f) do
  begin
   readln(f, buf);
   buf:=TrimStr(buf);
   if buf <> ''
    then
     begin
      SetLength(m, Length(m) + 1);
      while GetInteger(buf, int) do
       begin
        SetLength(m[High(m)], Length(m[High(m)]) + 1);
        m[High(m), High(m[High(m)])]:=int;
       end;
     end;
  end;
 CloseFile(f);
end;

PM MAIL ICQ   Вверх
MFSham
Дата 21.10.2005, 21:21 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 220
Регистрация: 28.8.2005
Где: Беларусь, Гродно

Репутация: 1
Всего: 3



Цитата(Zero @ 21.10.2005, 00:09)
MFSham ты пишешь, на паскале или делфи???

Пишу на делфях.

Цитата(Zero @ 21.10.2005, 00:09)
А тут, как в паскале:
код Pascal/Delphi
1:Close(f);

По моему компилятору абсолютно без разницы. Я могу и ошибаться, но оба случая у меня
работают одинаково.

Цитата(Zero @ 21.10.2005, 00:09)
У тебя строка:
код Pascal/Delphi
1:mas[count,i]:=StrToInt(str[i]);

Присваевает значение str[i], <кол-во символов в строке> раз, а потом только выполняется инкремент:
код Pascal/Delphi
1:inc(count);

Не знаю что ты тут увидел, но по моему все правильно smile

Цитата(Zero @ 21.10.2005, 00:09)
Ты пытаешся путём открытия в записанные данные переприсвоить значения:
Для этого напиши заместо команды Reset(f) --> ReWrite(f), т.е. создание по томуже пути будет, или др. словами перезапись....

Аналогично. И зачем тут ReWrite(f)??? smile

Цитата
Если Вы приведете пример самой худшей ситуации, то к нему будет очень просто сделать решение...

Никакого апокалипсиса с взятием данных из файла не предвидется smile
Ввод данных абсолютно корректный, и тем болле матрица квадратная с элементами 0 и1.

И короче, я нашел свою ошибку!-)
Код

program Project1;

{$APPTYPE CONSOLE}

uses
  SysUtils;
  
var
    i,j, count : byte;
    str : string;
    mas : array of array of integer;

begin
    AssignFile(f,'data.txt');
    Reset(f);
      count:=0;
      while not eof(f) do
        begin
           readln(f,str);
           if str<>'' then
           inc(count);
        end;
    setlength(mas,count,count);
    CloseFile(f);  

    count:=0;
    Reset(f);
      while not eof(f) do
         begin
            readln(f,str);
            if str<>'' then
            for j:=0 to length(str)-1 do
               mas[count,j]:=StrToInt(str[j+1]);
            inc(count);
         end;
     CloseFile(f);

    for i:=0 to High(mas) do
       begin
            for j:=0 to High(mas) do
             write(mas[i,j],' ') ;
             writeln;
       end;
   
    readln;
end.

Спасибо за помощь!

--------------------
Без ветра трава неподвижна. Без программ компьютеры бесполезны.
PM MAIL   Вверх
Самурай
Дата 21.10.2005, 22:09 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 64
Регистрация: 20.10.2005
Где: Воронежская облас ть > Семилуки

Репутация: 1
Всего: 1



MFSham, А мой вариант? Он универсален для любого вида файла и не бегает по нму несколько раз...
PM MAIL ICQ   Вверх
MFSham
Дата 22.10.2005, 00:03 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 220
Регистрация: 28.8.2005
Где: Беларусь, Гродно

Репутация: 1
Всего: 3



Цитата
MFSham, А мой вариант?

Я не спорю про универсальность алгоритма. Но если данные подаются на ввод в нормальном виде, то нафига изобретать велосипед, хотя это тоже полезно.
Цитата
Он универсален для любого вида файла и не бегает по нему несколько раз...

Несколько раз... Всего лишь 2 раза. Первый узнать количество строк, второй - загнать в массив. Вот собстна и усе.

--------------------
Без ветра трава неподвижна. Без программ компьютеры бесполезны.
PM MAIL   Вверх
Самурай
Дата 22.10.2005, 08:48 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 64
Регистрация: 20.10.2005
Где: Воронежская облас ть > Семилуки

Репутация: 1
Всего: 1



Цитата(MFSham @ 22.10.2005, 01:03)
Всего лишь 2 раза.

Проблема траты времени будет стоять в том случае, если я засуну в файл n-строк при n > 1000, что вполне может быть реальным для проектов.

Цитата(MFSham @ 22.10.2005, 01:03)
если данные подаются на ввод в нормальном виде

Есть гарантия этого? smile
PM MAIL ICQ   Вверх
MFSham
Дата 22.10.2005, 13:52 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 220
Регистрация: 28.8.2005
Где: Беларусь, Гродно

Репутация: 1
Всего: 3



Цитата
Есть гарантия этого?

Естественно, никакой гарантии нет, но данную матрицу в файл вводишь ты, не а левый юзер.
И всегда можно проверить корректность ввода данных.

Цитата
если я засуну в файл n-строк при n > 1000

Да, тогда с быстротой обработки инфы получится не очень хорошо, но в моем случае
кол-во строк врятли превысит 20. Так что ничего критического не предвидется!-) smile
--------------------
Без ветра трава неподвижна. Без программ компьютеры бесполезны.
PM MAIL   Вверх
Самурай
Дата 22.10.2005, 14:08 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 64
Регистрация: 20.10.2005
Где: Воронежская облас ть > Семилуки

Репутация: 1
Всего: 1



Цитата(MFSham @ 22.10.2005, 14:52)
И всегда можно проверить корректность ввода данных.

А зачем проверять корректность данных, если сразу можно распознавать строчку с учетом корректности?
PM MAIL ICQ   Вверх
MFSham
Дата 22.10.2005, 14:17 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 220
Регистрация: 28.8.2005
Где: Беларусь, Гродно

Репутация: 1
Всего: 3



Цитата
если сразу можно распознавать строчку с учетом корректности

Т.к. данные вводишь ТЫ, и если руки не из того места smile, то нужно распознавать строчку с
учетом корректности. А если руки из того места, то тебе, я думаю, не составит туда ввести
матрицу 10x10 с элементами 0 и1 просто без пробелов. Ась?
--------------------
Без ветра трава неподвижна. Без программ компьютеры бесполезны.
PM MAIL   Вверх
Самурай
Дата 22.10.2005, 14:19 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 64
Регистрация: 20.10.2005
Где: Воронежская облас ть > Семилуки

Репутация: 1
Всего: 1



MFSham
А если этот файл делает "секретарша", у которой интеллект и уровень образования ниже плинтуса? Надо в проектах все предусматривать... smile
PM MAIL ICQ   Вверх
Ответ в темуСоздание новой темы Создание опроса
Правила форума "Delphi: Общие вопросы"
SnowyMetalFan
bemsPoseidon
Rrader

Запрещается!

1. Публиковать ссылки на вскрытые компоненты

2. Обсуждать взлом компонентов и делиться вскрытыми компонентами

  • Литературу по Дельфи обсуждаем здесь
  • Действия модераторов можно обсудить здесь
  • С просьбами о написании курсовой, реферата и т.п. обращаться сюда
  • Вопросы по реализации алгоритмов рассматриваются здесь
  • 90% ответов на свои вопросы можно найти в DRKB (Delphi Russian Knowledge Base) - крупнейшем в рунете сборнике материалов по Дельфи


Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Snowy, MetalFan, bems, Poseidon, Rrader.

 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | Delphi: Общие вопросы | Следующая тема »


 




[ Время генерации скрипта: 0.0607 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.