2008年5月15日木曜日

VC++2005/2008 マネージ 線形リスト クラス

VC++2005/2008 マネージ 線形リスト クラス

マネージで線形リストが扱えるクラス(List.h)を作りました。マネージでは new の代わりに gcnew を使用するため、関数のスコープが外れたときでも gcnew で確保した内容が消えないようにしなければなりません。
以下は、線形リストで追加と削除ができるクラスです。先入れ先出のみの対応で、リストの真ん中に対して挿入・削除は対応しておりません。

**** List.h ****
#pragma once

using namespace System;
using namespace System::ComponentModel;
using namespace System::Collections;
using namespace System::Windows::Forms;
using namespace System::Data;
using namespace System::Drawing;

///------------------------------------------------
/// ■リストタイプクラスの先頭
///------------------------------------------------
ref class CListType
{
public: Int32 no; // リスト番号
public: array<unsigned char>^ buff; // 格納データ
public: Int32 len; // 文字数
public: CListType^ next; // 次の要素へのポインタ
///------------------------------------------------
/// コンストラクタ
///------------------------------------------------
public: CListType(Int32 length)
{
buff = gcnew array<unsigned char>(length);
len = length;
next = nullptr;
}
///------------------------------------------------
}; // ■クラスの最後
///------------------------------------------------


///------------------------------------------------
/// ■リストクラスの先頭
///------------------------------------------------
ref class CList
{
///------------------------------------------------
/// テーブル宣言
///------------------------------------------------
public: CListType^ head; // リストの先頭要素(ダミー)
public: CListType^ p;
public: CListType^ q;
public: CListType^ newcell;
public: CListType^ output;
public: Int32 No;
///------------------------------------------------
/// コンストラクタ
///------------------------------------------------
public: CList()
{
head = gcnew CListType(1); // リストヘッダー宣言
No = 0;
}
///------------------------------------------------
/// 追加
///------------------------------------------------
public: bool addlist(CListType^ input)
{
p = head->next; // 先頭要素の次の要素のアドレス
q = head; // 先頭要素のアドレス
while( p != nullptr )
{
q = p; // 追加位置の直前の要素のnextを後で設定するために、追加位置の直前の要素のアドレスを記憶しておく
p = p->next; // 次の要素へ進む
}

newcell = gcnew CListType(input->len); // 新しく追加する要素のためのメモリ領域を確保する
if( newcell == nullptr ){
return false; // メモリ不足
}

input->no = ++No;
for(Int32 ii=0; ii<(input->len); ii++){
newcell->buff[ii] = input->buff[ii]; // 新しい要素のデータを設定
}
newcell->len = input->len; // 文字数設定
newcell->next = p; // 新しい要素の次の要素へのアドレスを設定
q->next = newcell; // 新しい要素の直前の要素のnextに、新しい要素のアドレスを設定
return true;
}
///------------------------------------------------
/// 削除
///------------------------------------------------
public: CListType^ deletelist(void)
{
p = head->next; // 先頭要素の次の要素のアドレス
q = head; // 先頭要素のアドレス

if( p == nullptr ){ // リストの末尾
return nullptr;
}
else{
output = gcnew CListType(p->len); // 取出領域確保
output->no = --No;
for(Int32 ii=0; ii<(p->len); ii++){
output->buff[ii] = p->buff[ii]; // 新しい要素のデータを設定
}
output->len = p->len;

q->next = p->next; // 削除する要素の直前の要素のnextポインタを再設定
delete p;
}
return output;
}

///------------------------------------------------
}; // ■クラスの最後
///------------------------------------------------

0 件のコメント: