Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "Основная";
Текущий архив: 2002.04.22;
Скачать: [xml.tar.bz2];

Вниз

Pascal срочно, плзззз...   Найти похожие ветки 

 
cok   (2002-03-30 14:55) [0]

Я сейчас пишу прогу на Паскале, вот. Проблева в следующем:
у меня есть число в 10-ной системе счисления, я перевожу его в 2-ую сист.сч., меняю местами некоторые 1 и 0, а потом перевожу это в 10-ую сист.сч, но число больше 6000, и поэтому, когда я его перевожу в 2-ую сист. по длине оно будет ого го, т.е длиннее чем LongInt! Я пытался использовать тип comp или extended, но тогда прога не правильно будет переводить число в 10-ую сист. сч. Че делать?


 
Anatoly Podgoretsky   (2002-03-30 14:58) [1]

С какой стати у числа изменится размер от замены 0-1.
Паскаль правильно переводит и в comp и в extended, у тебя где то ошибка.
"Че делать?!" - быть конкретнее, без подземного стука.


 
drpass   (2002-03-30 15:46) [2]

Видишь ли, компьютер все числа хранит в двоичной системе, а десятичная, шестнадцатеричная и т.д. - это всего лишь формат ввода/вывода. Если тебе хочется поменять несколько битов, ничего никуда не нужно переводить


 
cok   (2002-03-30 19:36) [3]

>Anatoly Podgoretsky © (30.03.02 14:58)
>С какой стати у числа изменится размер от замены 0-1.
Размер у числа изменится, если я его из 10-ной сист.сч. переведу в 2-ую. Например, 11=1011, (цифр в два раза больше стало!)



 
Fay   (2002-03-31 05:12) [4]

2cok
Не надо Вам так отвечать Anatoly Podgoretsky. Это уважаемый мастер.
Вопрос Ваш приведённой формулировке - полный бред (так мне кажется). Пожалуйста, уточните.


 
Anatoly Podgoretsky   (2002-03-31 10:19) [5]

Так ты про текст, а чего тогда приплел LongInt, да еще и comp вместе с extended.
Кажетмя полное непонимание, не мешало бы повнятнее.
Что такое числа и какие у них ограничения можешь посмотреть в хелпе по теме "About types" если тебе это поможет, очень уж запущено.

Fay © (31.03.02 05:12)
Как видишь не очень :-)


 
Rooman   (2002-03-31 10:53) [6]

Кранты! Мастера как дети отвечать стали! Куда мир катится!
Ответ на вопрос: чтобы поменять биты в числе совершенно не надо его ни во что конвертировать. Делаешь так:

var i:longint;

...
i:=6000;
...
//изменение нулевого бита на противоположный:
i:=i xor 1;
//обнуление нулевого бита:
i:=i and not 1;
//присвоение нулевому биту единицы:
i:=i or 1;

//тоже самое для пятого бита, к примеру
//изменение пятого бита на противоположный:
i:=i xor 32;
//обнуление пятого бита:
i:=i and not 32;
//присвоение пятому биту единицы:
i:=i or 32;

Число, которое будет у тебя вместо 1 или 32 вычисляется по формуле: число = 2 в степени номер_бита;





 
dymka   (2002-03-31 10:54) [7]

Как уже сказал drpass, переводить для смены бит ничего не нужно... Существует такое понятие как битовые операции...
Это not, or, and, xor, shr итп... Поизучив их внимательнее, ты вероятно сможешь найти решение...
Второе - раз уж ты вздумал перевести десятичное число в двоичное, то количество цифр будет определятся логарифмом по основанию 2 плюс единица... поэтому нетрудно заметить, что число 6000 займет log2(6000) + 1 = 13.6 т.е. 13 разрядов...
Поэтому проще использовать строку для двоичного представления числа, кстати обмен битами в этом случае будет намного проще...


 
dymka   (2002-03-31 10:56) [8]

2Rooman - он похоже не биты инвертировать собрался, а менять местами - тобишь пятый бит поставить на первое место, ну а первый на пятое...


 
Anatoly Podgoretsky   (2002-03-31 11:08) [9]

Rooman © (31.03.02 10:53)
Так у него проблема с

"но число больше 6000, и поэтому, когда я его перевожу в 2-ую сист. по длине оно будет ого го, т.е длиннее чем LongInt!"


 
Rooman   (2002-03-31 11:11) [10]

2dymka - булева алгебра нужна здесь для понимания сути. Алгоритм, основаный на булевой алгебре, работает много эффективнее, чем возиться со строками, имхо:)

Обмен битами можно сделать так:

Например, меняем нулевой и первый биты местами:

var i,j,k:longint;
...
i:=254;
//обмен 0 и 1 битов местами
j:=i and 1;//выделили нулевой бит
k:=i and 2;//выделили первый бит
if k>0 then i:=i or 1 else i:=i and not 1;
if j>0 then i:=i or 2 else i:=i and not 2;



 
Song   (2002-03-31 11:13) [11]

Если нужно написать операцию перевода bin <--> dec таким корявым алгоритмом, то нужно эти разряды которые после перевода "будут больше чем убирается в LongInt" надо хранить только в ShortString, а уж никак не в Int переменных.


 
dymka   (2002-03-31 11:24) [12]

2Rooman - а никто и не спорит... :).
Но вдруг ему захочется все-таки перевести в двоичную строку :)
меняем i и j бит местами:


var
TempChar: char;
...
TempChar := BitStr[i];
BitStr[i] := BitStr[j];
BitStr[j] := TempChar;

Ну здесь еще такая фишка - нулевой бит это первый символ :)


 
Rooman   (2002-03-31 11:28) [13]

Короче, дело к ночи:)
Вот вам функция, которая меняет два любых бита в числе:

procedure swapbits(BitPos1,BitPos2:byte;var Number:longint);
var i1,i2,j,k:longint;
begin
i1:=1;
i2:=i1;
i1:=i1 shl BitPos1;
i2:=i2 shl BitPos2;
j:=Number and i1;
k:=Number and i2;
Number:=Number or i2 or i1;
if j=0 then Number:=Number xor i2;
if k=0 then Number:=Number xor i1;
end;


 
Rooman   (2002-03-31 11:30) [14]

P.S. меняет местами! Позиции битов нумеруются от 0 до 31!


 
dymka   (2002-03-31 11:33) [15]

ес чо, то допустима такая конструкция

i1 := 1 shl BitPos1;
i2 := 1 shl BitPos2;


 
Rooman   (2002-03-31 11:35) [16]

согласен:)


 
Rooman   (2002-03-31 11:37) [17]

2dymka - только в твоем варианте код компилируется неоптимально, хотя в данном случае это не критично.


 
Rooman   (2002-03-31 12:08) [18]

А вот более оптимальный вариант той-же функции:

procedure swapbits(BitPos1,BitPos2:byte;var Number:longint);
var i1,i2,m:longint;tmp:byte;
begin
if BitPos1>BitPos2 then
begin
tmp:=BitPos1;
BitPos1:=BitPos2;
BitPos2:=tmp;
end;
i1:=1;
i2:=i1;
i1:=i1 shl BitPos1;
i2:=i2 shl BitPos2;
m:=BitPos2-BitPos1;
Number:=(Number and not(i1 or i2))xor (((Number and i1) shl m)xor((Number and i2) shr m));
end;


 
cok   (2002-03-31 15:03) [19]

Простите, если невнятно объяснил суть задачи.
Приведу полный ее текст:
Дано целое десятичное число N (1<=N<=65535). Некто записал это число в двоичном формате и стал циклически сдвигать вправо, затем брать последнюю цифру числа и переносить ее в начало. Например, если N=11, то в 2-ом формате это 1011. После 1-го сдвига получим 1101, после 2-го - 1110, после 3-го 0111, после 4-го - исходное число 1011. Видно, что максимальное значение из всех полученных имеет число 1110, и это значение завно 14.
Требуется создать прогу, по которой для заданного числа N определяется максимальное значение числа, которое получится в результате вышеописанных сдвигов.


 
Anatoly Podgoretsky   (2002-03-31 15:19) [20]

И всего то?

max := N;
for i := 1 to 16 do begin
F := N and 1;
M := N shr 1;
if F = 1 then N or $8000;
if N > Max then Max := N;
end;


 
Rooman   (2002-03-31 15:53) [21]

интересно, где такою задачу применить можно?


 
JibSkeart   (2002-03-31 15:56) [22]

65535 = FFFF = 16bit ??
255 = FF = 8bit ??
Нет а что незя использовать массив ??
помойму проше ...
(То есть переводишь в двоичный .. 0 и 1 бросаешь в массив
по порядку как есть :)
а сдвигать байты мона и в массиве сразу ..
)

я тут пример для 8 бит набросал перевода из битов в десятичное число
Program Test;
Uses
Crt;
Type
t=Array [0..7] of Byte; {or [0..31] !!! }
t1=^t;
Var
x:Word;
s:T1;
begin
ClrScr;
New(s);
s^[0]:=1; s^[1]:=0; s^[2]:=0; s^[3]:=0; s^[4]:=1; s^[5]:=0; s^[6]:=0;
s^[7]:=0; {10010b=34d}
asm
xor bx,bx
les di,[s]
mov al,[es:di]
shl al,1
add bl,al
mov al,[es:di+1]
shl al,2
add bl,al
mov al,[es:di+2]
shl al,3
add bl,al
mov al,[es:di+3]
shl al,4
add bl,al
mov al,[es:di+4]
shl al,5
add bl,al
mov al,[es:di+5]
shl al,6
add bl,al
mov al,[es:di+6]
shl al,7
add bl,al
mov al,[es:di+7]
shl al,8
add bl,al
{ ... }
mov x,bx
end;

Writeln(x);
Dispose(s);
end.

А вообше сдеся Вам инфы сказали люди предостаточно ...

Да и Помоему на Асме есть та функция которая передвигает биты (в лево и в право)причем с переносом битов (если я не ошибаюсь)


 
JibSkeart   (2002-03-31 16:06) [23]

Да а нужно ли все енти переводы оттуда туда
всмысле из десятичной в двоичную и ....


 
Rooman   (2002-03-31 16:14) [24]

в ассемблере есть инструкции

ROR register,count - циклическое вращение вправо
ROL register,count - циклическое вращение влево

в связи с этим код Анатолия Подгорецкого упрощается:

var NNN:word;
...
asm
mov ax,NNN
mov dx,ax
mov cx,16
@1:
ror dx,1
cmp ax,dx
jb @2
mov ax,dx
@2:
loop @1
mov NNN,ax
end;

коротко и быстро!


 
JibSkeart   (2002-03-31 16:32) [25]

Rooman ©
Угу точно
Ну немного опередил меня ... :))


 
Anatoly Podgoretsky   (2002-03-31 17:16) [26]

Rooman © (31.03.02 16:14)
Я не был уверен, что допустимы асм коды, но могу поправить код, а то он с ошибкой, не учитывается 32 битная математика.
Во первых превратив его в функцию

function MaxCombo(N: Word) : Word;
asm
mov dx,ax
mov ecx,16
@1:
ror dx,1
cmp ax,dx
jb @2
mov ax,dx
@2:
loop @1
end;


 
Rooman   (2002-03-31 18:23) [27]

да, Анатолий, ecx не заметил... опечаточка вышла...


 
Rooman   (2002-03-31 18:25) [28]

Вот на все бы вопросы такие ответы были - красота! :)))


 
Anatoly Podgoretsky   (2002-03-31 19:06) [29]

Вот если бы не приходилось вытягивать, что именно нужно, была бы красота


 
JibSkeart   (2002-03-31 19:36) [30]

Вопервых если он пишет на паскале под досем ...
то сакс
он не поддерживает 32-х битные регистры .. :((
можно но только на TASMe или MASME написать и в OBJ
а потом оттуда ... но енто ...

function MaxCombo(N: Word) : Word;assembler еще одна поправка
asm
mov dx,ax
mov ecx,16 --- есх 32-х битный да и зачем ?? ты все рано значение для шетчика пихаеш 16 а может быть 32 ??
@1:
ror dx,1
cmp ax,dx
jb @2
mov ax,dx
@2:
loop @1
end;

да и к томуже по его словам
N (1<=N<=65535).

и не нужна 32 битная математика .65535= 16 бит


 
Anatoly Podgoretsky   (2002-03-31 19:55) [31]

Ты видимо не представляешь как работает команда loop в 32 битном компиляторе, так вот она учитывает не только cx, но и e.
К тому же ты путаешь 32 битный счетчик с 16 битными рабочими регистрами ax, dx

Во вторых по твоим словам в старом турбо паскале нельзя использовать асмь команды, только TASM или MASM, это не так, начиная с версии 6, можно напрямую, а до этого inline
вот в 16 разрядном компиляторе, конечно нужно mov cx,16


 
JibSkeart   (2002-03-31 20:05) [32]

насчет ecx 32 я мог ошибится так как с 32-х битным счетчиком
я не сталкивался (не приходилось)

//Во вторых по твоим словам в старом турбо паскале нельзя использовать асмь команды, только TASM или MASM, это не так, начиная с версии 6, можно напрямую, а до этого inline

про Tasm, Masm я имелл виду то что так можно работать с 32 бит рег.

но не имелл ввиду то что паскаль не знает асма
А с 32б мона работать и через db константы ...
на пискале (досявом)


 
Rooman   (2002-03-31 20:25) [33]

Уже начиная с 386 процессора LOOP оперирует с 32-разрядным счетчиком:)


 
Anatoly Podgoretsky   (2002-03-31 20:27) [34]

Ну ок уточнили.


 
Anatoly Podgoretsky   (2002-03-31 20:44) [35]

может и 16 и 32 зависит от префикса, но это не касается Дельфи, только 32


 
cok   (2002-03-31 21:49) [36]

>Anatoly Podgoretsky © (31.03.02 15:19)
>max := N;
>for i := 1 to 16 do begin
> F := N and 1;
> M := N shr 1;
> if F = 1 then N or $8000;
> if N > Max then Max := N;
>end;


> M := N shr 1; Здесь, наверно, надо написать N:=N shr 1;
> if F = 1 then N or $8000; Здесь ошибка, но не пойму какая.







 
cok   (2002-03-31 21:51) [37]

>JibSkeart © (31.03.02 19:36)
Твой код работает неверно!


 
Anatoly Podgoretsky   (2002-03-31 22:11) [38]

У сеня что буква М, конечно исправь
И здесь конечно, код писался быстро

if F = 1 then N := N or $8000;

Мог бы догадаться


 
cok   (2002-04-01 14:22) [39]

2 Anatoly Podgoretsky ©
Я так и догадался, но все равно работает НЕВЕРНО.


 
Alx2   (2002-04-01 14:57) [40]

Вот вариант на "чистом" ObjectPascal:

Function rormax(Val: Word): Word;
Var
K, HigherBitPos, LowBit: Integer;
Begin
Result := Val;
If Val = 0 Then exit;
HigherBitPos := trunc(ln(Val) / ln(2));
For K := 0 To HigherBitPos Do
Begin
LowBit := Val And 1;
Val := (Val Shr 1) Or (LowBit Shl HigherBitPos);
If Val > Result Then Result := Val;
End;
End;




Страницы: 1 2 вся ветка

Форум: "Основная";
Текущий архив: 2002.04.22;
Скачать: [xml.tar.bz2];

Наверх





Память: 0.54 MB
Время: 0.007 c
1-69770
Джафар
2002-04-10 08:41
2002.04.22
Как подключитькомпонент ?


1-69781
Darlok
2002-04-09 17:47
2002.04.22
Dll


14-70021
KvORubin
2002-03-17 18:24
2002.04.22
RichEdit - как в нём отобразить непечатаемые символы (как в M.Office)


3-69692
Sirus
2002-03-30 11:02
2002.04.22
Hello кул программеры... тут проблемка с DCOM


14-69981
Philipps
2002-03-14 09:40
2002.04.22
Как сделать proxy сервер на делфи?





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский