Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > IT форум > Помощь студентам
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 17.07.2010, 07:08   #1
Lion-Tiger
Пользователь
 
Регистрация: 25.01.2009
Сообщений: 43
По умолчанию [Delphi] Как задать массив строк целиком?

Я создаю компонент и мне нужно в нем реализовать свойство - массив строк. Все уже готово и работает, если вместо массива строк взять TStrings, но я стремлюсь к изяществу и например, если мне нужно задать сразу весь этот массив строк, то с TStrings придется делать вот так:
Код:
MyProperty.Text:=Value1+#13#10+Value2+#13#10+ и так далее...
И хотелось бы все это делать примерно так, как реализовано в методе канвы Polygon:
Код:
Canvas.Polygon([point1,point2,point3 ....])

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

TStrAr = array of string;

property MyProperty:TStrar
 read GetMyproperty
 write SetMyProperty;

а задавать само свойство из программы вот так:

MyProperty:=[value1,value2,value3 .....]
Но когда я прописываю все это в программе, при попытке присвоить свойству массив строк, как в последнем примере выдает ошибку
Ordinal type required

Хотелось бы иметь возможность целиком задать массив так же красиво, как в последнем примере - через запятую значения.

Подскажите, как правильно делать свойства-массивы и как добиться, чтобы можно было удобно задавать все свойство целиком, а не по отдельным элементам массива
Lion-Tiger вне форума Ответить с цитированием
Старый 17.07.2010, 09:33   #2
Alex Cones
Trust no one.
Старожил
 
Аватар для Alex Cones
 
Регистрация: 07.04.2009
Сообщений: 6,526
По умолчанию

А SetLength не думаете вставлять?
SQUARY PROJECT - НАБОР БЕСПЛАТНЫХ ПРОГРАММ ДЛЯ РАБОЧЕГО СТОЛА.
МОЙ БЛОГ
GRAY FUR FRAMEWORK - УДОБНАЯ И БЫСТРАЯ РАЗРАБОТКА WINAPI ПРИЛОЖЕНИЙ
Alex Cones вне форума Ответить с цитированием
Старый 18.07.2010, 07:11   #3
Lion-Tiger
Пользователь
 
Регистрация: 25.01.2009
Сообщений: 43
По умолчанию

При чем тут SetLength?? Он нужен просто для работы с массивами, а к ошибке он не имеет никакого отношения, или я не прав??
Если я не прав, то как мне следует использовать SetLength???
Признаюсь, я не уточнил, что у меня с массивом тоже все безупречно работает, кроме возможности сразу задать массив, см. первый пост.
Lion-Tiger вне форума Ответить с цитированием
Старый 18.07.2010, 07:57   #4
Smitt&Wesson
Старожил
 
Аватар для Smitt&Wesson
 
Регистрация: 31.05.2010
Сообщений: 13,543
По умолчанию

На счёт Delphi не скажу, не знаю, но на С++, можно изящьно всё зделать при помощи контейнеров последовательностей. Например так:
#include <vector>
using namecpace std;
.......
vector <TStrings> Vector;
Пиши пьяным, редактируй трезвым.
Справочник по алгоритмам С++ Builder
Smitt&Wesson вне форума Ответить с цитированием
Старый 18.07.2010, 07:57   #5
VintProg
not
Участник клуба
 
Аватар для VintProg
 
Регистрация: 27.06.2009
Сообщений: 1,399
По умолчанию

Цитата:
но я стремлюсь к изяществу и например
В смысле???
Нежели вы в строку хочите вводить бинарные числа??

MyProperty.Text:=Value1+#13#10+Valu e2+#13#10+ и так далее...

или как???

Что имено в TStrings не устраивает?
VintProg вне форума Ответить с цитированием
Старый 18.07.2010, 10:12   #6
Serge_Bliznykov
Старожил
 
Регистрация: 09.01.2008
Сообщений: 26,229
По умолчанию

можно вот так:
Код:
type
  TForm1 = class(TForm)
    Button1: TButton;
    procedure TStrArrAdd(const A : array of string);
    procedure Button1Click(Sender: TObject);
  private
    MyArray : array of string;
    { Private declarations }
  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

{$R *.DFM}

procedure TForm1.TStrArrAdd(const A : array of string);
var i : integer;
begin
  for i:=Low(A) to High(A) do
    MyArray[i] := A[i];
end;

procedure TForm1.Button1Click(Sender: TObject);
begin
  SetLength(MyArray,5);
  TStrArrAdd(['Строка1','Строка2','33','44','Строка 5']);
end;
Serge_Bliznykov вне форума Ответить с цитированием
Старый 19.07.2010, 08:54   #7
Stilet
Белик Виталий :)
Старожил
 
Аватар для Stilet
 
Регистрация: 23.07.2007
Сообщений: 57,097
По умолчанию

Цитата:
Serge_Bliznykov
Доведем до кондиции:
Код:
procedure TForm1.TStrArrAdd(const A : array of string);
var i : integer;
begin  
  SetLength(MyArray,Length(a));
  for i:=Low(A) to High(A) do
    MyArray[i] := A[i];
end;

procedure TForm1.Button1Click(Sender: TObject);
begin
  TStrArrAdd(['Строка1','Строка2','33','44','Строка 5']);
end;
Ато мало ли как там девки запляшут
I'm learning to live...
Stilet вне форума Ответить с цитированием
Старый 19.07.2010, 09:18   #8
Lion-Tiger
Пользователь
 
Регистрация: 25.01.2009
Сообщений: 43
По умолчанию

Не получается, все равно выдает ошибку Ordinal type required!
Привожу код, который у меня:
Код:
unit LTFieldBox; //юнит моего компонента
......
{Fields}

  TLTFieldBoxFieldValues = array of string;

  TLTFieldBoxField = class(TCollectionItem)
  private
    { Private declarations }

    //Переменная к св-ву Values
    FValues:TLTFieldBoxFieldValues; 

    //Переменная к св-ву ValueCount
    FValueCount:integer;

    //Процедуры к св-ву Values
    function GetValues: TLTFieldBoxFieldValues;
    procedure SetValuesProp(const Value: TLTFieldBoxFieldValues);

  protected
    { Protected declarations }

    //Количество значений, равное количеству колонок
    property ValueCount:integer
      read FValueCount
      write SetValueCount;

    //Процедура служит для того, чтобы задавать массив значений целиком,
    //вместо присваивания св-ву
    procedure SetValues(const Value: TLTFieldBoxFieldValues);
  published
    { Published declarations }

    //Св-во возвращает значения поля
    property Values:TLTFieldBoxFieldValues
      read GetValues
      write SetValuesProp;
...........

  TLTFieldBoxFields = class(TCollection)
...........

function TLTFieldBoxField.GetValues: TLTFieldBoxFieldValues;
begin
  result:=FValues;
end;

procedure TLTFieldBoxField.SetValues(const Value: TLTFieldBoxFieldValues);
var i:integer;
begin                                            
  //Устанавливаем длину нашего массива равной полученному
  setlength(FValues,length(Value));
  //Проходим по всем элементам полученного массива
  for i:=0 to length(Value)-1 do
    //и присваиваем их значения основному массиву
    FValues[i]:=Value[i];
  //Устанавливаем необходимую длину нашему массиву
  setlength(FValues,FValueCount);
end;

procedure TLTFieldBoxField.SetValuesProp(const Value: TLTFieldBoxFieldValues);
begin
  FValues:=Value;

  //Обновляем количество значений
  setlength(FValues,FValueCount);
end;
А это юнит программы, в которой компонент тестю:
Код:
unit Unit1;

Uses TLTFieldBox;
.......

var
  Form1: TForm1; 
  FB:TLTFieldBox;

......
procedure TForm1.FormCreate(Sender: TObject);
begin
     fb:=TLTFieldBox.Create(self);
     fb.Fields.Add.SetValues(['Первый','Тест №1','Тестик №1','4']); //При компиляции тут возникает ошибка, описанная выше
end;
Пояснения:

Компонент (TLTFieldBox) представляет таблицу, где есть поля (строки) и колонки.

Поля (TLTFieldBoxFields) представляют собой коллекцию (TCollection), одно поле (TLTFieldBoxField) - элемент коллекции (TCollectionItem).

Аналогично с колонками (Коллекция и т п)

В компоненте доступ к полям получается через св-во Fields, а к колонкам через Columns.

Values - массив значений поля, они связаны с коллекцией колонок, по индексам (Values[Index]=>Columns[Index]) каждому значению соответствует колонка.

ValueCount - количество колонок, нужно, чтобы нормально работать с массивом значений.

Вот-с...

Еще раз повторюсь, что так - все безупречно работает, то есть
fb.Fields.Add.Values[0]:='Первый';
Компилируется без ошибок и работает.
Всяких глупых предложений типа:
"Вдруг, длина массива не соответствует","Надо setlength использовать"
и т п....
Больше прошу не писать.
Все везде проверил, все работает, кроме этого момента (См Название темы и первый пост).

Жду конструктивных предложений =))
Если чего-то не хватает, пишите

Думаю, если сейчас проблема с этой ошибкой решится, то и присвоить массив св-ву получится...
Lion-Tiger вне форума Ответить с цитированием
Старый 19.07.2010, 09:40   #9
Utkin
Старожил
 
Аватар для Utkin
 
Регистрация: 04.02.2009
Сообщений: 17,351
По умолчанию

Не нашел в Вашем коде описания:
fb.Fields.Add.SetValues
Опишите Type для TLTFieldBox
Маньяк-самоучка
Utkin появился в результате деления на нуль.
Осторожно! Альтернативная логика
Utkin вне форума Ответить с цитированием
Старый 19.07.2010, 11:51   #10
Lion-Tiger
Пользователь
 
Регистрация: 25.01.2009
Сообщений: 43
По умолчанию

Add - метод TCollection, добавляет новый элемент
Код:
TLTFieldBoxFields = class(TCollection)
..........
public
.........
function Add:TLTFieldBoxField;
........
function TLTFieldBoxFields.Add: TLTFieldBoxField;
begin
  Result:=TLTFieldBoxField(inherited Add);

  //Обновляем количество значений
  Result.ValueCount:=ValueCount;
end;
А что значит это??
Цитата:
Опишите Type для TLTFieldBox
Код:
TLTFieldBox = class(TCustomControl)
Lion-Tiger вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Как задать в массив значение ячейки? StudentofSUSU Microsoft Office Excel 1 07.01.2010 23:43
Задать двумерный массив (матрицу) 6х4 zergon Помощь студентам 3 04.01.2010 00:29
как задать массив в программе? m.a.x.i.m Помощь студентам 14 12.12.2009 13:40
задать массив как константу...нужен совет dead-vip Паскаль, Turbo Pascal, PascalABC.NET 5 21.12.2008 16:07
задать массив типа X: array [0..N] of integer -где N переменная читаеться из EditBox Kivin13 Общие вопросы Delphi 22 06.09.2007 09:25