Ошибка DCC ...: E2010 Несовместимые типы: 'integer' и 'Integer' - PullRequest
1 голос
/ 05 ноября 2011

Попытка построить интерфейс и общий граф и получить странную ошибку - обратите внимание на регистр различий в слове «целое число» в строке ошибки.

Анализатор текста передается в реализацию Graph, а затем вызывается Graph для построения его базовой структуры данных. Далее объекты IGraphConstructor могут строить более сложные фактические графики, а не просто заполнить базовый словарь.

IGraphConstructor<K,V> = interface
  function Construct(AData : TObjectDictionary<K,V>) : boolean;
end;

IGraph<K,V> = interface
  ['{B25EEE1F-3C85-43BB-A56B-3E14F7EA926C}']
  function Construct(AConstructor : IGraphConstructor<K,V>) : boolean;
  function GetNodes : TObjectDictionary<K,V>;
  property Nodes : TObjectDictionary<K,V> read GetNodes;
end;

TGraph<K,V> = class(TComponent, IGraph<K,V>)
private
  FData : TObjectDictionary<K,V>;
  function GetNodes : TObjectDictionary<K,V>;
... 

//the editor
TVirtualEditor = class(TComponent)
private
  FGlyphs : TGraph<integer,TGlyph>;
...  

TTextParser<integer,TGlyph> = class(TInterfacedObject, IGraphConstructor<integer,TGlyph>)
... 

и ...

function TVirtualEditor.Edit(AText: string): boolean;
var
  parser : TTextParser<integer,TGlyph>;
begin
  parser := TTextParser<integer,TGlyph>.Create(AText);
  result := FGlyphs.Construct(parser);
end;

function TTextParser<integer,TGlyph>.Construct(AData: TObjectDictionary<integer,TGlyph>): boolean;
var
  i : integer;
begin
  for i := 1 to length(FText) do
  begin
    //#1
    AData.AddOrSetValue(i, TGlyph(TCharGlyph.Create( FText[i] )) ); //!--> error [DCC Error] ...: E2010 Incompatible types: 'integer' and 'Integer'
  end;

  //uc....

end;

Объявление TTextParser как TTextParser<K,V> и использование его как

TParser : TTextParser<integer,TGlyph>;

возвращает и ошибка на # 1 из

[DCC Error] ...: E2010 Incompatible types: 'K' and 'Integer'

РЕДАКТИРОВАТЬ: Обходной путь

Нашел обходной путь, но не уверен, что это способ сделать это.

function TTextParser<K,V>.Construct(AData: TObjectDictionary<K,V>): boolean;
var
  i : integer;
  n : K;
  o : V;
begin
  for i := 1 to length(FText) do
  begin
    n := K((@i)^);
    o := V(TCharGlyph.Create( FText[i] ));
    AData.AddOrSetValue(n, o );
  end;
  result := true;
end;

Ответы [ 2 ]

5 голосов
/ 05 ноября 2011

Строка

TTextParser<integer,TGlyph> = class(TInterfacedObject, IGraphConstructor<integer,TGlyph>)

описывает универсальный тип, где используются два имени универсального типа: integer и TGlyph (например, K и V находятся в IGraph<K,V>).Это только заполнители, и их не следует путать с существующими типами integer и TGlyph.

1 голос
/ 07 ноября 2011

Я предполагаю, что вы хотели добиться какого-то особого поведения, если K является целым числом.Это называется специализация и возможно в C ++ ( ссылка на статью в журнале MSDN, посвященную шаблонной специализации ), но не в Delphi.Лучше избегать таких специализаций и просто работать с универсальным типом K (это должно быть легко, иначе универсальный класс не имеет особого смысла в первую очередь).

Существует обходной путь, если вам действительно нужен особый случай: вы можете сравнить информацию типа (для этого вам нужно указать единицу измерения TypInfo):

if (TypeInfo(K) = TypeInfo(Integer)) then
  begin
  // special case
  end;
...