template <typename T>
Это действительно нужно параметризовать?Казалось бы, любая величина сдвига может быть сохранена в size_t
, и преобразование в size_t
неявно или явно было бы хорошей идеей перед началом остальной части процесса.
integer operator<<(T shift){
Обычно двоичный operator
функции лучше всего реализованы как не-члены friend
s.Например, при создании указателя this
учитывается меньше преобразований, чем для общих операндов.Я бы написал friend integer operator<< ( integer lhs, size_t shift )
.
std::list <uint8_t> out = value;
Если вы используете friend
и передачу по значению, то эта копия создается неявно.Компилятору также легче избавиться от него, если вы на самом деле просто изменяете один объект, например q = q << 3
.
for(unsigned int i = 0; i < (shift >> 3); i++)// get rid of bytes if shift > 8
Будьте осторожны в условиях цикла.Вы применяете оператор к высокоуровневому типу, который может вызвать дорогостоящие вычисления (или даже бесконечную рекурсию, если T
равен integer
!
shift &= 7; // shift by less than a byte
На данный момент, если shift == 0
все готово. Лучше всего вставить условное return
здесь. Кроме того, теперь диапазон ограничен действительно , поэтому присвойте более узкий тип, чем T
.
out.push_front(0); // extra byte for overflow
Этонеобходим только в том случае, если байт будет отличен от нуля. Вероятно, лучше всего выполнить специальный случай для первой операции и сделать условным push_front
вместо специального случая для последнего.
... Хм, он выглядит как operator>>
выполняется больше… переход к этому…
for(; i != j; i++){
i++;
uint8_t temp = *i << (8 - shift);
i--;
*i += temp;
}
*j >>= shift;
Очевидно, что оператор >>
отсутствует в цикле. Попробуйте *i = *i >> shift + temp
. Кроме того, я не вижу, как список становится короче.Это сделано в integer::integer( list<…> )
?
Однако я не могу реально увидеть, что вызывает поведение в опубликованном выводе. Ведущий ноль, вероятно, является результатом безусловного push_front
в operator<<
, нообразец, который я ожидал бы, является c
, 6
, 3
, 18
, c
,….Кажется, вы не повторяете какую-либо последовательность, но вместо этого переходите случайным образом.
Может быть, код деления или конструктор класса могли бы дать подсказки.