typedef struct CvSeq {
int flags; // miscellaneous flags
int header_size; // size of sequence header
CvSeq* h_prev; // previous sequence
CvSeq* h_next; // next sequence
CvSeq* v_prev; // 2nd previous sequence
CvSeq* v_next // 2nd next sequence
int total; // total number of elements
int elem_size; // size of sequence element in byte
char* block_max; // maximal bound of the last block
char* ptr; // current write pointer
int delta_elems; // how many elements allocated
// when the sequence grows
CvMemStorage* storage; // where the sequence is stored
CvSeqBlock* free_blocks; // free blocks list
CvSeqBlock* first; // pointer to the first sequence block
}
จะเห็นมีข้อมูลที่สำคัญอยู่คือ total ที่บอกจำนวนในลิสต์ กับ pointer สำหรับ linked list สี่ตัวคือ h_prev, h_next, v_prev, v_next เป็น linked list ที่ชี้ได้สี่ทิศเลยทีเดียว
โดยตามปกติเช่นเดียว linked list ทั่วไป sequence จะสามารถจัดการข้อมูลที่อยู่บนหัวท้ายได้ดีกว่าข้อมูลที่อยู่ตรงกลาง
โดยปกติ ฟังก์ชันใน OpenCV จะสร้าง sequence ให้เราโดยอัตโนมัติ เราแค่เรียกใช้ sequence ให้ถูกก็พอ ในกรณีที่ต้องการสร้างและลบ sequence เอง ใช้คำสั่งต่อไปนี้
CvSeq* cvCreateSeq(
int seq_flags,
int header_size,
int elem_size,
CvMemStorage* storage
);
แล้วลบด้วย
void cvClearSeq(
CvSeq* seq
);
sequence ใช้หน่วยความจำใน memory storage (ที่ผ่าน parameter ใน cvCreateSeq) ในตอนที่ใช้คำสั่ง cvClearSeq หน่วยความจำจะไม่ถูก recycle (อ้างอิงจากตอนที่แล้ว เรื่อง memory storage)
คำสั่งจริงๆ ที่น่าจะใช้ของ sequence น่าจะเป็นการเข้าถึง object ใน sequence มากกว่า ลองดูคำสั่งตัวอย่างในหนังสือ
for( int i=0; i
CvPoint* p = (CvPoint*)cvGetSeqElem ( seq, i );
printf(“(%d,%d)\n”, p->x, p->y );
}
จะเป้นการใช้คำสั่ง cvGetSeqElem โดยใส่ sequence เป็นพารามิเตอร์และ index i ที่ต้องการอย่าลืม casting ให้เป็นข้อมูลทีเราต้องการด้วย
คำสั่งอื่นๆ ในการจัดการ sequence จะขอลิสต์ไว้ ต่อไปนี้
คำสั่งในการ ค้นหา element ใน sequence
- cvSeqElemIdx
- cvCloneSeq
- cvSeqSlice
- cvRemoveSlice
- cvInsertSlice
- cvSeqSort
- cvSeqSearch
- cvSeqInvert
- cvSeqPartition
typedef int (*CvCmpFunc)(const void* a, const void* b, void* userdata );
การใช้ sequence เป็น stack (สองหัวด้วยนะ)
- cvSeqPush
- cvSeqPop
- cvSeqPushFront
- cvSeqPopFront
- cvSeqPushMulti
- cvSeqPopMulti
การแทรก element กลาง sequence
- cvSeqInsert
- cvSeqRemove
การเปลี่ยนขนาด memory block size (จะได้ใช้เหรอ)
- cvSetBlockSize
- cvCvtSeqToArray
- cvMakeSeqHeaderForArray
ส่วนสุดท้ายคือการอ่านเขียน sequence ซึ่งมีประสิทธิภาพมากกว่าการ insert การ ใช้ฟังก์ชัน cvGetSeqElem โดยใช้วิธีสร้างตัว sequence reader กับ sequence writer ขึ้นมา การจัดการดูแล้วเหมือนการอ่านเขียนไฟล์ใน C
คำสั่งที่เกี่ยวข้องกับ sequence writer
- cvStartWriteSeq
- cvStartAppendToSeq
- cvEndWriteSeq
- cvFluseSeqWriter
- CV_WRITE_SEQ_ELEM
- CV_WRITE_SEQ_ELEM_VAR
คำสั่งที่เกี่ยวข้องกับ sequence reader
- cvStartReadSeq
- cvGetSeqReaderPos
- cvSetSeqReaderPos
- CV_NEXT_SEQ_ELEM
- CV_PREV_SEQ_ELEM
- CV_READ_SEQ_ELEM
- CV_REV_READ_SEQ_ELEM
เนื่องจากการเขียนใน sequence writer น่าจะสำคัญจะอาจจะได้ใช้ เลยยกตัวอย่างในหนังสือมาเสียหน่อย
We will create a writer and append a
hundred random points drawn from a 320-by-240 rectangle to the new sequence.
CvSeqWriter writer;
cvStartWriteSeq( CV_32SC2, sizeof(CvSeq), sizeof(CvPoint), storage, &writer );
for( i = 0; i < 100; i++ )
{
CvPoint pt; pt.x = rand()%320; pt.y = rand()%240;
CV_WRITE_SEQ_ELEM( pt, writer );
}
CvSeq* seq = cvEndWriteSeq( &writer );
No comments:
Post a Comment