Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Низкоуровневое программирование > Assembler - Ассемблер (FASM, MASM, WASM, NASM, GoASM, Gas, RosAsm, HLA) и не рекомендуем TASM
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 05.09.2014, 13:06   #1
Biohazard
Пользователь
 
Регистрация: 23.02.2009
Сообщений: 78
По умолчанию бинарная длина целого числа

Доброго времени суток уважаемые форумчане.

есть число X, как мы знаем в памяти оно хранится как набор единиц и нулей например 13 это 1101 и т д

задача: узнать положение ближайшей единицы, то-есть, четвертая с конца, значит бинарный размер = 4

предполагаю что делается на asm, благо в делфи его можно прикручивать.

пытался сделать через trunc(log2(abs(x))+1), работало, но использование функций, работающих с ieee745 или как его там, к сожалению запрещено,

подскажите, как можно найти позицию единички?
заранее благодарю
Biohazard вне форума Ответить с цитированием
Старый 05.09.2014, 13:22   #2
waleri
Старожил
 
Регистрация: 13.07.2012
Сообщений: 6,331
По умолчанию

подсчитайте сколько раз можно поделить на 2 без остатка.
waleri на форуме Ответить с цитированием
Старый 05.09.2014, 13:25   #3
Biohazard
Пользователь
 
Регистрация: 23.02.2009
Сообщений: 78
По умолчанию

Цитата:
Сообщение от waleri Посмотреть сообщение
подсчитайте сколько раз можно поделить на 2 без остатка.
это конечно гениально и я бы никогда не додумался, но работает это медленно и подход не верный. реализация уже есть, но для чисел, типа in64 достаточно больших работает медленно, да и использовать деление, когда я уверен что можно просто как то прочесть память, не совсем правильный подход. была бы задача столь тривиальной, я бы не спрашивал, в asm-е кто нибудь тут разбирается?
Biohazard вне форума Ответить с цитированием
Старый 05.09.2014, 13:48   #4
Serge_Bliznykov
Старожил
 
Регистрация: 09.01.2008
Сообщений: 26,229
По умолчанию

Biohazard, как это может долго работать?!!

Код:
var k : integer;
  N : int64;
begin
  N :=  787789000098000;
  k := 0;
  while N>0 do begin
    inc(k);
    N := N shr 1
  end;
  ShowMessage('бинарная длина числа = '+IntToStr(k))
end;
думаю, что подобный код на современном процессоре может подсчитает более пяти миллионов чисел за секунду... Вам нужно быстрее?
Serge_Bliznykov вне форума Ответить с цитированием
Старый 05.09.2014, 13:58   #5
waleri
Старожил
 
Регистрация: 13.07.2012
Сообщений: 6,331
По умолчанию

Цитата:
Сообщение от Biohazard Посмотреть сообщение
была бы задача столь тривиальной, я бы не спрашивал, в asm-е кто нибудь тут разбирается?
Ну тогда нате: http://graphics.stanford.edu/~seander/bithacks.html
Там есть и алгоритм перевертывания данных + алгоритм поиска наиболее старшего бита.
waleri на форуме Ответить с цитированием
Старый 05.09.2014, 14:02   #6
Biohazard
Пользователь
 
Регистрация: 23.02.2009
Сообщений: 78
По умолчанию

Цитата:
Сообщение от Serge_Bliznykov Посмотреть сообщение
Biohazard, как это может долго работать?!!

Код:
var k : integer;
  N : int64;
begin
  N :=  787789000098000;
  k := 0;
  while N>0 do begin
    inc(k);
    N := N shr 1
  end;
  ShowMessage('бинарная длина числа = '+IntToStr(k))
end;
думаю, что подобный код на современном процессоре может подсчитает более пяти миллионов чисел за секунду... Вам нужно быстрее?
Код:
  function GetCount(const Base:byte;X:Int64):cardinal;//для любой системы измерения
  var
    z:int64;
    zp:cardinal;
    Base3:cardinal;
    xx:int64;
  begin
    Result:=0;
    Base3:=Base*Base*base;//увеличиваем скорость
    xx:=0;
    while X>0 do
    begin
      z:=1;
      zp:=0;
      while X>=Z do
      begin
        Z:=Z*base3;
        xx:=X;
        X:=X div Z;
        inc(zp,3);
        inc(Result,zp);
      end;
    end;
    if(xx<>0)and(X=0)then//исправляем потери
    begin
      Z:=Z div (Base*Base);
      xx:=xx div Z;
      if(xx=0)then
        dec(Result,2)
      else
      if(xx<base)then
        dec(Result,1);
    end;
  end;
с этого и начинал, немножко ускорил 10 000 000 за 3 секунды, но к сожалению недостаточно, встроенный в делфи логарифм2 справляется быстрее на больших числах "9223372036854775807"
Biohazard вне форума Ответить с цитированием
Старый 05.09.2014, 14:03   #7
f.hump
C/C++, Asm
Участник клуба
 
Аватар для f.hump
 
Регистрация: 02.03.2010
Сообщений: 1,323
По умолчанию

__asm {

BSR rax, [N]
INC rax
MOV [k], rax

}
f.hump вне форума Ответить с цитированием
Старый 05.09.2014, 14:20   #8
Biohazard
Пользователь
 
Регистрация: 23.02.2009
Сообщений: 78
По умолчанию

Цитата:
Сообщение от f.hump Посмотреть сообщение
__asm {

BSR rax, [N]
INC rax
MOV [k], rax

}
Спасибо, в асме я не силён, компилятор делфей ругается, может что то не так применяю?

Код:
function rax(N:int64):byte;
asm
  BSR rax, [N]
  INC rax
  MOV [k], rax
end;
можете пояснить?

Последний раз редактировалось Biohazard; 05.09.2014 в 14:23.
Biohazard вне форума Ответить с цитированием
Старый 05.09.2014, 14:31   #9
f.hump
C/C++, Asm
Участник клуба
 
Аватар для f.hump
 
Регистрация: 02.03.2010
Сообщений: 1,323
По умолчанию

то что я написал, оно для х64

для 32х бит (если N 64-х битное) можно как-то так


LEA edx, [N]

CMP DWORD PTR [edx+4], 0
JZ nohigh
BSR eax, [edx+4]
ADD eax, 33
JMP done
nohigh:

BSR eax, [edx]
INC eax

done:
; MOV [k], eax

Последний раз редактировалось f.hump; 05.09.2014 в 14:43. Причина: ошибочко
f.hump вне форума Ответить с цитированием
Старый 05.09.2014, 14:36   #10
Biohazard
Пользователь
 
Регистрация: 23.02.2009
Сообщений: 78
По умолчанию

эх, на первую строку ругается, говорит [Error] Unit1.pas(38): Invalid register combination ну и т д, ладно, всё равно спасибо, попытаюсь дальще сам додуматься)
Biohazard вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
округление числа до целого johny_03 PHP 1 16.04.2014 08:51
Изъятие из целого числа нулей Sting95 Помощь студентам 2 31.03.2014 10:02
Угадывании целого числа vonavi98 Помощь студентам 0 15.01.2014 19:22
Visual Basic: Описать функцию DigitN (K, N) целого типа, возвращающую N-ю цифру целого положительного числа К Екатерина23 Помощь студентам 1 10.12.2013 09:25
Вывести числа целого неотр. числа Gonzo Помощь студентам 11 04.05.2010 16:55