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

Поиск:

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


Новичок



Профиль
Группа: Участник
Сообщений: 36
Регистрация: 10.3.2006

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



пишу простой интерпретатор, данные в нем представленны как variant, при попытке работы с ним вылазит ошибка
First chance exception at $77E73887. Exception class EVariantTypeCastError with message 'Could not convert variant of type (Array Variant) into type (String)'. Process Project4.exe (2104)

но там, где она брякается, нет такого преобразования smile 

как её побороть?

код

Код

program Project4;

{$APPTYPE CONSOLE}

uses
  Variants,SysUtils;

type
Tvar = record
 name,data:variant;
end;
Tconsole = class
  variables:array of Tvar;
  function eval(s:string):variant;
  function find(s:string;p:variant):variant;
  function setvar(p:variant):variant;
  function getvar(p:variant):variant;
end;

function Tconsole.eval(s:string):variant;
var p,c,res:string;i,j,g,a,z,x:integer; state:(start,exite,comm,cons,par,go);
arpar:variant;
begin
arpar:=vararraycreate([0,9],varVariant);
i:=0;
j:=0;
g:=0;
a:=0;
x:=0;
trim(s);
state:=start;
z:=length(s);
 repeat
 if state=start then
  begin
   if i>=z then state:=exite;
   if s[i]=';' then state:=go;
   if s[i]='(' then
    begin
    g:=1;
    state:=par;
    end;
   if s[i]='{' then state:=comm;
   if s[i]='/' then state:=cons;
   if (not(s[i]=' '))and(state=start) then
    begin
    {c[j]:=s[i];}
    insert(copy(s,i,1),c,j);
    j:=j+1;
    end;
   i:=i+1;
  end;
 if state=comm then
  begin
  if s[i]='}' then state:=start;
  i:=i+1;
  end;
 if state=cons then
  begin
  insert(copy(s,2,z),res,0);
  result:=res;
  state:=exite;
  end;
 if state=par then
  begin
  if s[i]=')' then g:=g-1;
  if s[i]='(' then g:=g+1;
  if s[i]=',' then
    begin
    arpar[x]:=eval(p);
    x:=x+1;
    end;
  if not(g=0) then
    begin
    {p[a]:=s[i];}
     a:=a+1;
    insert(copy(s,i,1),p,a);
    end;
  if g=0 then state:=start;
  i:=i+1;
  end;
 if state=go then
  begin
  delete(c,j,1);
  arpar:=find(c,arpar);
  result:=arpar[1];
  state:=start;
  x:=0;
  end;

 until state=exite;


end;

function Tconsole.find(s:string;p:variant):variant;
begin
if s='eval' then result:=eval(p);
if s='print' then writeln(p);
if s='con' then result:=p;
end;

function Tconsole.setvar(p:variant):variant;
var pp,names,dates:string; i,j,a:integer;
begin
i:=0;
j:=0;
a:=0;
pp:=p;

end;
function Tconsole.getvar(p:variant):variant;
begin

end;

var
cons:Tconsole; con:string;
begin
  { TODO -oUser -cConsole Main : Insert code here }
  cons:=Tconsole.Create;
  repeat
  readln(con);
  cons.eval(con);
  until false;
end.


delphi 2005
PM MAIL ICQ   Вверх
ama_kid
Дата 3.4.2007, 17:36 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


АСУТП-кодер
***


Профиль
Группа: Комодератор
Сообщений: 1460
Регистрация: 5.3.2007
Где: Москва

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



не совсем понял, зачем ты так сложно пытаешься сделать интерпретатор (его можно сделать гораздо легче), но ошибка у тебя возникает, из-за того, что ты всегда в функцию find передаешь unassigned аргумент (у тебя нет финального присваивания параметра после того, как ты сдетектировал закрывающуюся скобку). Я написал так:
Код

  if s[i]=')' then
   begin
    arpar:=p;
    g:=g-1;
   end;
  if s[i]='(' then g:=g+1;

и команда 
Цитата
print(123); 
вывела мне строчку 123. Ясно, что это полумера, но просто у тебя очень уж много косячков в коде (взять хотя бы такой момент - функция find у тебя возвращает unassigned во всех случаях кроме заданных тобой, и в случае некорректного ввода параметров (print 123; )в дальнейшем присвоении - будет AV). В общем, тут надо идеологию менять, мне кажется... 
P.S. Я писал когда-то интерпретатор - я просто сканил строку до первого пробела и это получалась команда, а все остальное я скармливал рекурсивной функции разбора параметров, но у меня там были на каждом шагу проверки от некорректности ввода (чего у тебя нигде нет). 
P.P.S. Зачем тебе тип variant - я тоже не понял, ведь все вводится в строковом виде, который ты всегда можешь преобразовать в нужный тебе, да еще и с проверкой на правильность и с корректной обработкой исключений...


--------------------
самурай без меча подобен самураю с мечом, но только без меча 
PM MAIL   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума "Delphi: Для новичков"
SnowyMetalFan
bemsPoseidon
Rrader

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

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

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

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


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

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


 




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


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

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