50 #define MY_LOG_DEBUG_ID(x)
103 void set(
const KEY &
x,
const unsigned int sid)
114 return s <<
"<str_id=" <<
x.str_id <<
"> " <<
x.k <<
" ";
188 template <
class T,
class Key>
197 unsigned short level;
214 unsigned long *streamsize;
221 unsigned long basesize;
225 em_buffer(
const unsigned short i,
const unsigned long bs,
226 const unsigned int ar);
272 for (
unsigned int i = 0; i < index; i++) {
289 return (
unsigned long)pow((
double)arity, (
double)level - 1) * basesize;
297 return streamsize[i] - deleted[i];
304 unsigned long tot = 0;
305 for (
unsigned int i = 0; i < index; i++) {
337 long insert(T *a,
long n);
366 s <<
"BUFFER_" <<
b.level <<
": ";
372 for (
unsigned int i = 0; i <
b.index; i++) {
373 b.print_stream(s, i);
387 void print_stream(ostream &s,
unsigned int i);
394 char *get_stream_name(
unsigned int i)
const;
397 void print_stream_names();
402 void check_name(
unsigned int i);
408 template <
class T,
class Key>
410 const unsigned int ar)
411 : arity(ar), level(i), basesize(bs)
417 snprintf(str,
sizeof(str),
418 "em_buffer: allocate %d AMI_STREAM*, total %ld\n", arity,
425 snprintf(str,
sizeof(str),
"em_buffer: allocate deleted array: %ld\n",
426 (
long)(arity *
sizeof(
long)));
428 deleted =
new long[arity];
431 snprintf(str,
sizeof(str),
"em_buffer: allocate streamsize array: %ld\n",
432 (
long)(arity *
sizeof(
long)));
434 streamsize =
new unsigned long[arity];
438 snprintf(str,
sizeof(str),
"em_buffer: allocate name array: %ld\n",
439 (
long)(arity *
sizeof(
char *)));
441 name =
new char *[arity];
446 if ((!data) || (!deleted) || (!streamsize)) {
447 cerr <<
"em_buffer: cannot allocate\n";
453 for (
unsigned int ui = 0; ui < arity; ui++) {
471 template <
class T,
class Key>
473 : level(buf.level), basesize(buf.basesize), index(buf.index),
481 for (
unsigned int i = 0; i < index; i++) {
490 deleted[i] = buf.deleted[i];
491 streamsize[i] = buf.streamsize[i];
496 name[i] = buf.name[i];
505 template <
class T,
class Key>
512 for (
unsigned int i = 0; i < index; i++) {
535 template <
class T,
class Key>
539 #ifdef EMBUF_CHECK_NAME
540 assert(i >= 0 && i < index);
544 data[i]->name(&fooname);
545 #ifdef EMBUF_CHECK_NAME_PRINT
546 cout <<
"::check_name: checking stream [" << level <<
"," << i
547 <<
"] name:" << fooname << endl;
550 if (strcmp(
name[i], fooname) != 0) {
551 cerr <<
"name[" << i <<
"]=" <<
name[i] <<
", streamname=" << fooname
563 template <
class T,
class Key>
573 if (data[i] ==
NULL) {
580 #ifdef EMBUF_PRINT_GETPUT_STREAM
581 cout <<
"get_stream:: name[" << i <<
"]=" <<
name[i] <<
" from disk\n";
587 if ((fp = fopen(
name[i],
"rb")) ==
NULL) {
588 cerr <<
"get_stream: checking that stream " <<
name[i]
612 assert(data[i]->stream_len() == streamsize[i]);
622 template <
class T,
class Key>
632 if (data[i] !=
NULL) {
639 #ifdef EMBUF_PRINT_GETPUT_STREAM
640 cout <<
"put_stream:: name[" << i <<
"]=" <<
name[i] <<
" to disk\n";
659 template <
class T,
class Key>
665 #ifdef EMBUF_PRINT_GETPUT_STREAMS
666 cout <<
"em_buffer::get_streams (buffer " << level <<
")";
667 cout <<
": index = " << index <<
"(arity=" << arity <<
")\n";
671 for (
unsigned int i = 0; i < index; i++) {
684 template <
class T,
class Key>
690 #ifdef EMBUF_PRINT_GETPUT_STREAMS
691 cout <<
"em_buffer::put_streams (buffer " << level <<
")";
692 cout <<
": index = " << index <<
"(arity=" << arity <<
")\n";
696 for (
unsigned int i = 0; i < index; i++) {
706 template <
class T,
class Key>
710 assert(i >= 0 && i < index);
718 template <
class T,
class Key>
722 for (i = 0; i < index; i++) {
724 cout <<
"stream " << i <<
": " <<
name[i] << endl;
732 template <
class T,
class Key>
737 #ifdef EMBUF_CLEANUP_PRINT
740 cout <<
"before cleanup:\n";
741 print_stream_names();
742 print_stream_sizes();
752 unsigned int i, empty = 0;
753 for (i = 0; i < index; i++) {
755 if (get_stream_len(i) == 0) {
757 #ifdef EMBUF_DELETE_STREAM_PRINT
758 cout <<
"deleting stream [" << level <<
"," << i <<
"]:";
789 #ifdef EMBUF_DELETE_STREAM_PRINT
790 cout <<
"em_buffer::cleanup: shifting streams\n";
793 for (i = 0; i < index; i++) {
800 deleted[j] = deleted[i];
801 streamsize[j] = streamsize[i];
823 assert(index == j + empty);
826 #ifdef EMBUF_DELETE_STREAM_PRINT
827 cout <<
"em_buffer::cleanup: index set to " << index << endl;
835 #ifdef EMBUF_CLEANUP_PRINT
838 cout <<
"after cleanup:\n";
839 print_stream_names();
840 print_stream_sizes();
849 template <
class T,
class Key>
856 for (
unsigned int i = 0; i < index; i++) {
858 assert(streamsize[i] == data[i]->stream_len());
881 template <
class T,
class Key>
886 MEMORY_LOG(
"em_buffer::sort: allocate new AMI_STREAM\n");
902 aerr = substream_merge(data, arity, sorted_stream);
907 return sorted_stream;
918 template <
class T,
class Key>
929 for (i = 0; i < arity; i++) {
936 std::vector<T *> in_objects(
941 snprintf(str,
sizeof(str),
942 "em_buffer::substream_merge: allocate keys array, total %ldB\n",
951 keys =
new footype[arity];
958 for (i = 0; i < arity; i++) {
965 if ((ami_err = instreams[i]->read_item(&(in_objects[i]))) !=
968 in_objects[i] =
NULL;
976 Key k = in_objects[i]->getPriority();
981 unsigned int NonEmptyRuns = j;
990 ami_err = outstream->
seek(0);
992 while (!mergeheap.empty()) {
994 mergeheap.min(minelt);
997 if ((ami_err = outstream->
write_item(*in_objects[i])) !=
1002 if ((ami_err = instreams[i]->read_item(&(in_objects[i]))) !=
1010 mergeheap.delete_min();
1013 Key k = in_objects[i]->getPriority();
1015 mergeheap.delete_min_and_insert(nextit);
1032 template <
class T,
class Key>
1039 cout <<
"em_buffer::insert: buffer full\n";
1048 MEMORY_LOG(
"em_buffer::insert(from array): allocate AMI_STREAM\n");
1054 for (
long i = 0; i < n; i++) {
1080 template <
class T,
class Key>
1087 cout <<
"em_buffer::insert: buffer full\n";
1098 #ifdef EMBUF_CHECK_INSERT
1100 cout <<
"CHECK_INSERT: checking stream is sorted\n";
1114 assert(deleted[nextstream()] == 0);
1115 assert(streamsize[nextstream()] == 0);
1121 data[nextstream()] = str;
1122 deleted[nextstream()] = bos;
1123 streamsize[nextstream()] = str->
stream_len();
1128 name[nextstream()] = s;
1133 data[nextstream()] =
NULL;
1135 #ifdef EMBUF_PRINT_INSERT
1136 cout <<
"insert stream " << s <<
" at buf [" << level <<
"," << nextstream()
1144 #ifdef EMBUF_PRINT_INSERT
1145 print_stream_sizes();
1146 print_stream_names();
1155 return get_stream_len(nextstream() - 1);
1161 template <
class T,
class Key>
1166 assert((i >= 0) && (i < index));
1171 s <<
"STREAM " << i <<
": [";
1173 ae = data[i]->seek(deleted[i]);
1176 for (
long j = 0; j < get_stream_len(i); j++) {
1177 ae = data[i]->read_item(&
x);
1187 template <
class T,
class Key>
1196 for (
unsigned int i = 0; i < index; i++) {
1199 ae = data[i]->seek(deleted[i]);
1201 ae = data[i]->read_item(&
min);
1203 cout <<
min->getPriority() <<
"..";
1205 ae = data[i]->seek(streamsize[i] - 1);
1207 ae = data[i]->read_item(&
max);
1209 cout <<
max->getPriority() <<
" (sz=" << get_stream_len(i) <<
")] ";
1211 for (
unsigned int i = index; i < arity; i++) {
1220 template <
class T,
class Key>
1229 for (
unsigned int i = 0; i < index; i++) {
1231 ae = data[i]->seek(deleted[i]);
1233 for (
unsigned long j = 0; j < get_stream_len(i); j++) {
1234 ae = data[i]->read_item(&
x);
1236 cout <<
x->getPriority() <<
",";
1238 cout <<
"]" << endl;
1240 for (
unsigned int i = index; i < arity; i++) {
1249 template <
class T,
class Key>
1253 cout <<
"(streams=" << index <<
") sizes=[";
1254 for (
unsigned int i = 0; i < arity; i++) {
1255 cout << get_stream_len(i) <<
",";
1257 cout <<
"]" << endl;
@ AMI_ERROR_END_OF_STREAM
AMI_err write_item(const T &elt)
AMI_err name(char **stream_name)
AMI_err seek(off_t offset)
AMI_err read_item(T **elt)
void persist(persistence p)
unsigned int laststream() const
void incr_deleted(unsigned int i)
long insert(T *a, long n)
void print_stream_sizes()
unsigned short get_level() const
unsigned int nextstream() const
em_buffer(const unsigned short i, const unsigned long bs, const unsigned int ar)
unsigned long get_stream_len(unsigned int i)
long total_deleted() const
unsigned long get_buf_maxlen()
friend ostream & operator<<(ostream &s, em_buffer &b)
unsigned long get_buf_len()
unsigned long get_stream_maxlen() const
unsigned int get_nbstreams() const
AMI_STREAM< T > ** get_streams()
void put_stream(unsigned int i)
unsigned int get_arity() const
AMI_STREAM< T > * get_stream(unsigned int i)
friend int operator!=(const merge_key &x, const merge_key &y)
friend int operator<=(const merge_key &x, const merge_key &y)
friend merge_key operator+(const merge_key &x, const merge_key &y UNUSED)
void set(const KEY &x, const unsigned int sid)
friend int operator==(const merge_key &x, const merge_key &y)
unsigned int stream_id() const
friend ostream & operator<<(ostream &s, const merge_key< KEY > &x)
friend int operator>=(const merge_key &x, const merge_key &y)
merge_key(const KEY &x, const unsigned int sid)
friend int operator<(const merge_key &x, const merge_key &y)
friend int operator>(const merge_key &x, const merge_key &y)
#define MY_LOG_DEBUG_ID(x)
#define UNUSED
A macro for an attribute, if attached to a variable, indicating that the variable is not used.
#define assert(condition)
void MEMORY_LOG(const std::string &str)