Delphi4で作業中です。
StringGrid内の特定の文字列を探す方法はあるのでしょうか。
(=特定の文字列が書かれたStringGridを探し当てる)
ネット内ブラウジングしても「これだ」と思える記載が見つかりません。
できましたら早めのお教えをお願いします。
すみませんバージョンを4と打ち間違えましたがDelphi7です。
編集 削除セルの文字列と探したい文字列が一致する場合なら、
RowsプロパティやColsプロパティがTStringsなので、全行あるいは全列に対し、
ループ内でIndexOf メソッドを使えば、探せそうな気がします。
そうでない場合、セルの文字列をループで1つずつAnsiPos関数とかで確認する方法になるかと。
あると便利そうなので、それらしいのを作ってみました。
StringGridと変数を関数に入れると、
ヒットしたセルの数を返値に、
Stringlistに見つかった文字の位置を、
格納して返します。
ansipos_strgrid(
グリッドを指定;
=か<>を指定;
比較対象文字列を指定;
ヒットした座標を格納するStringlistを指定):integer;
例:
i := ansipos_strgrid(StringGrid1,'=','aaa',st);//aaaと一致する文字列を探します。
showmessage(inttostr(i) + '個見つかりました' + char(13) + st.Text);//結果を表示
※何分まだ未熟者ですので、この程度の簡易なものが限界ですが・・・。
function count_if_str(st,gety:tstringlist;s,set_str:string;int1:integer):integer;
var
i,i1,i2:integer;
st1,st2:TStringList;
s1,s2,s3:string;
function choice_if:string;
begin
choice_if := '';
if s = '=' then begin
if 0 < ansipos(set_str,s1) then begin
choice_if := st[i];
end;
end else if s = '<>' then begin
if 0 = ansipos(set_str,s1) then begin
choice_if := st[i];
end;
end else begin
//
end;
end;
begin
st1 := TStringList.Create;
st1.Clear;
st2 := TStringList.Create;
st2.Clear;
for i := 0 to st.Count -1 do begin
s1 := st[i];
s2 := '0';
s3 := '0';
if '' <> choice_if then begin
st1.Add(s1);
s2 := inttostr(int1);
s3 := inttostr(i);
st2.Add(s2 + ',' + s3);
end;
end;
count_if_str := st1.Count;
st1.Free;
gety.Text:= st2.Text;
st2.Free;
end;
function ansipos_strgrid(g:TStringGrid;s,set_str:string;st_ans:TStringList):integer;
var
st,st1,gety:TStringList;
i,i1,i2:integer;
begin
st :=TStringList.Create;
st.Clear;
st1 :=TStringList.Create;
st1.Clear;
gety :=TStringList.Create;
gety.Clear;
i2 := 0;
for i := 0 to g.ColCount -1 do begin
st_arry[i] := TStringList.Create;
st_arry[i].Clear;
gety.Clear;
st.Text:= g.Cols[i].Text;
i1 := count_if_str(st,gety,s,set_str,i);
st1.Text:= st1.Text + gety.Text;
i2 := i2 + i1;
end;
ansipos_strgrid:= i2;
st_ans.text := st1.text;
st.Free;
gety.Free;
end;
procedure TForm1.Button1Click(Sender: TObject);
var
st:TStringList;
begin
st := TStringList.Create;
st.Clear;
showmessage(inttostr(ansipos_strgrid(form1.StringGrid1,'=','aaa',st)));
showmessage(st.Text);
st.free;
end;
すいません、ansipos_strgrid関数に問題がありましたので修正します。
不要な変数の一部を消し忘れていましたので、修正しました。
function ansipos_strgrid(g:TStringGrid;s,set_str:string;st_ans:TStringList):integer;
var
st,st1,gety:TStringList;
i,i1,i2:integer;
begin
st :=TStringList.Create;
st.Clear;
st1 :=TStringList.Create;
st1.Clear;
gety :=TStringList.Create;
gety.Clear;
i2 := 0;
for i := 0 to g.ColCount -1 do begin
gety.Clear;
st.Text:= g.Cols[i].Text;
i1 := count_if_str(st,gety,s,set_str,i);
st1.Text:= st1.Text + gety.Text;
i2 := i2 + i1;
end;
ansipos_strgrid:= i2;
st_ans.text := st1.text;
st.Free;
gety.Free;
end;
私も作ってみました^^
procedure TForm1.FormCreate(Sender: TObject);
var
iwC, iwR: Word;
begin
//実験用データ
for iwR := 0 to Pred(StringGrid1.RowCount) do begin
for iwC := 0 to Pred(StringGrid1.ColCount) do begin
StringGrid1.Cells[iwC, iwR] := IntToStr(Random(1000));
end;
end;
end;
procedure TForm1.Button1Click(Sender: TObject);
var
iwC, iwR: Word;
begin
//500なら行列番号をリストに追加
for iwR := 0 to Pred(StringGrid1.RowCount) do begin
for iwC := 0 to Pred(StringGrid1.ColCount) do begin
if StringGrid1.Cells[iwC, iwR] = '500' then begin
ListBox1.Items.Add(IntToStr(iwC) + ',' + IntToStr(iwR));
end;
end;
end;
//50を含むなら行列番号をリストに追加
for iwR := 0 to Pred(StringGrid1.RowCount) do begin
for iwC := 0 to Pred(StringGrid1.ColCount) do begin
if Pos('50', StringGrid1.Cells[iwC, iwR]) <> 0 then begin
ListBox2.Items.Add(IntToStr(iwC) + ',' + IntToStr(iwR));
end;
end;
end;
end;
みなさま
ありがとうございました。
いただいたプログラムでなんとかいけそうです。
ちなみにプログラムが作れなかったら
例外処理をしてセル単位でなくカラム単位に
とぶようにしてしのごうと思っていました。