XOR

Для неординарных вопросов. Если вы опытный программист, попавший в трудную ситуацию, — вам сюда.

Модератор: gaidar

Правила форума
Этот раздел не предназначен для того, чтобы вы адресовали свою проблему профессионалам.
Этот раздел предназначен для профессионалов, которые столкнулись с проблемой и не могут решить ее самостоятельно.
Если вы считаете себя профессионалом, а свою проблему сложной — вам сюда.
Если модератор посчитает, что вы ошиблись, то на первый раз он перенесет ваше сообщение в основной раздел без последствий для автора. Во второй раз тема будет закрыта, а автору будет выписано нарушение. В третий раз автор будет забанен.
Antonariy
Повелитель Internet Explorer
Повелитель Internet Explorer
Аватара пользователя
 
Сообщения: 4824
Зарегистрирован: 28.04.2005 (Чт) 14:33
Откуда: Мимо проходил

XOR

Сообщение Antonariy » 14.07.2006 (Пт) 10:09

Рискну штоль...
Недавно узнал, что операция XOR выполняется вызовом функции __vbavarxor из msvbvm60.dll, что негативно сказывается на алгоритмах, ее использующих, например crc. В двоичных и битовых вычислениях я не очень копенгаген, в связи с чем вопрос: возможно ли заменить ее другими операциями?

Если нет, то как ее задекларировать? В каком-то топике прочитал, что декларирование функций msvbvm60.dll повышает их производительность.
Лучший способ понять что-то самому — объяснить это другому.

Nicky
Постоялец
Постоялец
 
Сообщения: 519
Зарегистрирован: 12.08.2004 (Чт) 12:14

Сообщение Nicky » 14.07.2006 (Пт) 10:59

A XOR B = (A AND NOT B) OR (B AND NOT A)
и совсем не страшно

ANDLL
Великий гастроном
Великий гастроном
Аватара пользователя
 
Сообщения: 3450
Зарегистрирован: 29.06.2003 (Вс) 18:55

Сообщение ANDLL » 14.07.2006 (Пт) 11:03

возможно ли заменить ее другими операциями?
Да, написание критических модулей на других языках.
В VB половина операций вызывает функции из msvbvm
Крайне сомниетельным представялется факт, что "декларирование функций msvbvm60.dll " тут чемто поможет.
Но ведь проверить не сложно? :roll:

2Nicky:Вероятно нелишним будет объянить к чему была приведенная формула?
Гастрономия - наука о пище, о ее приготовлении, употреблении, переварении и испражнении.
Блог

keks-n
Доктор VB наук
Доктор VB наук
Аватара пользователя
 
Сообщения: 2509
Зарегистрирован: 19.09.2005 (Пн) 17:17
Откуда: г. Москва

Сообщение keks-n » 14.07.2006 (Пт) 11:10

ANDLL
(A AND NOT B) OR (B AND NOT A) тоже самое, что и A XOR B
Изображение

Nicky
Постоялец
Постоялец
 
Сообщения: 519
Зарегистрирован: 12.08.2004 (Чт) 12:14

Сообщение Nicky » 14.07.2006 (Пт) 11:13

ANDLL писал(а):2Nicky:Вероятно нелишним будет объянить к чему была приведенная формула?

Antonariy писал(а):...в связи с чем вопрос: возможно ли заменить ее другими операциями?...

tyomitch
Пользователь #1352
Пользователь #1352
Аватара пользователя
 
Сообщения: 12822
Зарегистрирован: 20.10.2002 (Вс) 17:02
Откуда: חיפה

Сообщение tyomitch » 14.07.2006 (Пт) 11:40

Пойду по стопам ANDLL :-)

Исходник:
Код: Выделить всё
Option Explicit

Sub Main()
Dim a As Long, b As Long, c As Long
'если убрать строки, компилятор сразу подставит в c готовый результат ;-)
    a = "&H5A5A"
    b = "&HA5A5"
    c = a Xor b
    MsgBox c
End Sub


Скомпилированный:
Код: Выделить всё
6:        a = "&H5A5A"
0040161C   mov         edi,dword ptr [__imp_@__vbaI4Str (00401050)]
00401622   xor         esi,esi
00401624   push        offset ___vba@001BE140 (0040131c)
00401629   mov         dword ptr [c],esi
0040162C   mov         dword ptr [unnamed_var1],esi
0040162F   mov         dword ptr [unnamed_var1],esi
00401632   mov         dword ptr [unnamed_var1],esi
00401635   mov         dword ptr [unnamed_var1],esi
00401638   call        edi
7:        b = "&HA5A5"
0040163A   push        offset ___vba@001BE158 (00401330)
0040163F   mov         ebx,eax
00401641   call        edi
8:        c = a Xor b
00401643   xor         eax,ebx


Мораль: нечего верить всем подряд.
Изображение

Antonariy
Повелитель Internet Explorer
Повелитель Internet Explorer
Аватара пользователя
 
Сообщения: 4824
Зарегистрирован: 28.04.2005 (Чт) 14:33
Откуда: Мимо проходил

Сообщение Antonariy » 14.07.2006 (Пт) 12:17

Понятно. Может тогда __vbavarxor используется для переменных variant? Вот так он выглядит Variant XOR Variant
Код: Выделить всё
00401992: mov edi, MSVBVM60.DLL.__vbaVarCopy
00401998: xor esi, esi
0040199A: mov ebx, 00000008h
0040199F: mov var_78, esi
004019A2: lea edx, var_78
004019A5: lea ecx, var_24
004019A8: mov var_24, esi
004019AB: mov var_34, esi
004019AE: mov var_38, esi
004019B1: mov var_48, esi
004019B4: mov var_58, esi
004019B7: mov var_68, esi
004019BA: mov var_70, 00401604h ; &H5A5A
004019C1: mov var_78, ebx
004019C4: call edi
004019C6: lea edx, var_78
004019C9: lea ecx, var_34
004019CC: mov var_70, 00401618h ; &HA5A5
004019D3: mov var_78, ebx
004019D6: call edi
004019D8: lea eax, var_24
004019DB: lea ecx, var_34
004019DE: push eax
004019DF: lea edx, var_48
004019E2: push ecx
004019E3: push edx
004019E4: call Xor
А ASM, оказывается, прикольная штука :)
Лучший способ понять что-то самому — объяснить это другому.

tyomitch
Пользователь #1352
Пользователь #1352
Аватара пользователя
 
Сообщения: 12822
Зарегистрирован: 20.10.2002 (Вс) 17:02
Откуда: חיפה

Сообщение tyomitch » 14.07.2006 (Пт) 13:04

Восхищаюсь теми, кто догадался в алгоритмах типа CRC использовать варианты, и по этому судить о тормознутости VB.
:roll: :roll: :roll:
Изображение

Antonariy
Повелитель Internet Explorer
Повелитель Internet Explorer
Аватара пользователя
 
Сообщения: 4824
Зарегистрирован: 28.04.2005 (Чт) 14:33
Откуда: Мимо проходил

Сообщение Antonariy » 14.07.2006 (Пт) 13:43

Это был не я :D Я просто решил проверить, а не для variant'а ли __vbavarxor? В том источнике, откуда я про нее узнал не говорится, что она именно для variant. Там просто сказано, что она ксорит.
Лучший способ понять что-то самому — объяснить это другому.

Mao
Обычный пользователь
Обычный пользователь
Аватара пользователя
 
Сообщения: 95
Зарегистрирован: 10.10.2004 (Вс) 13:09

Сообщение Mao » 27.07.2006 (Чт) 17:04

Доброго времени суток.
Столкнулся с такой проблемой. Надо произвести такую операцию:
Код: Выделить всё
Currency And Currency

Мне подсказали что в VB6 оператор And, Or, Xor приводит свои аргументы к Long. Каким образом можно обойти данное ограничение?

uhm
Продвинутый гуру
Продвинутый гуру
Аватара пользователя
 
Сообщения: 1597
Зарегистрирован: 02.12.2004 (Чт) 15:21

Сообщение uhm » 27.07.2006 (Чт) 17:09

Кхм... а что должно получиться в результате операции Курренси энд Курренси?
Быть... или не быть. Вот. В чём вопрос?

Q2W
Постоялец
Постоялец
Аватара пользователя
 
Сообщения: 745
Зарегистрирован: 31.01.2004 (Сб) 20:46
Откуда: Питер

Сообщение Q2W » 27.07.2006 (Чт) 20:23

uhm писал(а):Кхм... а что должно получиться в результате операции Курренси энд Курренси?

Может много курренси?
Я знаю верный путь

Mao
Обычный пользователь
Обычный пользователь
Аватара пользователя
 
Сообщения: 95
Зарегистрирован: 10.10.2004 (Вс) 13:09

Сообщение Mao » 27.07.2006 (Чт) 22:42

uhm писал(а):Кхм... а что должно получиться в результате операции Курренси энд Курренси?

Попробуй выполнить след. код:
Код: Выделить всё
Dim s As Currency
s = 4294967295# And 3084996963#

Viper
Артефакт VBStreets
Артефакт VBStreets
Аватара пользователя
 
Сообщения: 4394
Зарегистрирован: 12.04.2005 (Вт) 17:50
Откуда: Н.Новгород

Сообщение Viper » 28.07.2006 (Пт) 7:06

А зачем интересно может понадобиться операция Currency And Currency в принципе?
Весь мир матрица, а мы в нем потоки байтов!

Mao
Обычный пользователь
Обычный пользователь
Аватара пользователя
 
Сообщения: 95
Зарегистрирован: 10.10.2004 (Вс) 13:09

Сообщение Mao » 28.07.2006 (Пт) 10:19

!Viper! писал(а):А зачем интересно может понадобиться операция Currency And Currency в принципе?

RC5-32

Viper
Артефакт VBStreets
Артефакт VBStreets
Аватара пользователя
 
Сообщения: 4394
Зарегистрирован: 12.04.2005 (Вт) 17:50
Откуда: Н.Новгород

Сообщение Viper » 31.07.2006 (Пн) 8:25

2 Мао, возможно тебе поможет прочтение описания типа CURRENCY в MSDN:

MSDN писал(а):This structure is used to store a currency value.
typedef CY CURRENCY;
Remarks
A currency number is stored as an 8-byte, two's complement integer, scaled by 10,000 to give a fixed-point number with 15 digits to the left of the decimal point and 4 digits to the right. This representation provides a range of 922337203685477.5807 to -922337203685477.5808. The CURRENCY data type is useful for calculations involving money, or for any fixed-point calculation where accuracy is particularly important.
The CURRENCY data type is defined as the union of a structure containing two bytes and a 64-bit integer, using the following code:
typedef union FARSTRUCT tagCY {
struct {
#ifdef _MAC
long Hi;
unsigned long Lo;
#else
unsigned long Lo;
long Hi;
#endif
};
LONGLONG int64;
} CY;
Весь мир матрица, а мы в нем потоки байтов!

tyomitch
Пользователь #1352
Пользователь #1352
Аватара пользователя
 
Сообщения: 12822
Зарегистрирован: 20.10.2002 (Вс) 17:02
Откуда: חיפה

Сообщение tyomitch » 31.07.2006 (Пн) 8:38

Viper, я не понимаю, как это описание может помочь.
Изображение

Viper
Артефакт VBStreets
Артефакт VBStreets
Аватара пользователя
 
Сообщения: 4394
Зарегистрирован: 12.04.2005 (Вт) 17:50
Откуда: Н.Новгород

Сообщение Viper » 31.07.2006 (Пн) 8:41

Оно может помочь понять бесполезность применения AND к Currency.
Весь мир матрица, а мы в нем потоки байтов!

tyomitch
Пользователь #1352
Пользователь #1352
Аватара пользователя
 
Сообщения: 12822
Зарегистрирован: 20.10.2002 (Вс) 17:02
Откуда: חיפה

Сообщение tyomitch » 31.07.2006 (Пн) 10:10

Возможно, он просто хранит в Currency 64-битные числа. Тогда применять к ним AND вполне осмысленно.

По сути вопроса: я бы сделал LSet в UDT из двух Long-ов, в ней сделал And, и затем LSet обратно. Не самый быстрый способ, но с ассемблерными вставками вряд ли будет быстрее.
Изображение

Viper
Артефакт VBStreets
Артефакт VBStreets
Аватара пользователя
 
Сообщения: 4394
Зарегистрирован: 12.04.2005 (Вт) 17:50
Откуда: Н.Новгород

Сообщение Viper » 31.07.2006 (Пн) 11:55

Я собственно и имел ввиду, что какой смысл использовать Currency, если сей тип по сути своей есть UDT из двух Long. Проще сразу писать 64-разрядное число в такую UDT и делать And над ней без дополнтельных преобразований.
Весь мир матрица, а мы в нем потоки байтов!

tyomitch
Пользователь #1352
Пользователь #1352
Аватара пользователя
 
Сообщения: 12822
Зарегистрирован: 20.10.2002 (Вс) 17:02
Откуда: חיפה

Сообщение tyomitch » 31.07.2006 (Пн) 12:07

Над Currency работают арифметические действия, а над UDT нет.
И ещё её можно передавать ByVal в функцию.
Изображение

Viper
Артефакт VBStreets
Артефакт VBStreets
Аватара пользователя
 
Сообщения: 4394
Зарегистрирован: 12.04.2005 (Вт) 17:50
Откуда: Н.Новгород

Сообщение Viper » 31.07.2006 (Пн) 12:16

уговорил! :D Да и присваивать/считывать значение Currency проще
Весь мир матрица, а мы в нем потоки байтов!

Mao
Обычный пользователь
Обычный пользователь
Аватара пользователя
 
Сообщения: 95
Зарегистрирован: 10.10.2004 (Вс) 13:09

Сообщение Mao » 03.08.2006 (Чт) 18:40

tyomitch писал(а):Возможно, он просто хранит в Currency 64-битные числа. Тогда применять к ним AND вполне осмысленно.

По сути вопроса: я бы сделал LSet в UDT из двух Long-ов, в ней сделал And, и затем LSet обратно. Не самый быстрый способ, но с ассемблерными вставками вряд ли будет быстрее.

Так если оператор And приводит свои аргументы к Long, чем это может помочь?

GSerg
Шаман
Шаман
 
Сообщения: 14286
Зарегистрирован: 14.12.2002 (Сб) 5:25
Откуда: Магадан

Сообщение GSerg » 03.08.2006 (Чт) 19:34

Тем, что поDWORDный AND имеет тот же эффект, что и AND на всё сразу.
Как только вы переберёте все варианты решения и не найдёте нужного, тут же обнаружится решение, простое и очевидное для всех, кроме вас

Mao
Обычный пользователь
Обычный пользователь
Аватара пользователя
 
Сообщения: 95
Зарегистрирован: 10.10.2004 (Вс) 13:09

Сообщение Mao » 05.10.2006 (Чт) 16:41

Подскажите, почему так:
Код: Выделить всё
Public Type int64
    lowD As Long
    highD As Long
End Type
Public Type curUDT
    num As Currency
End Type

Dim a As int64, b As curUDT
b.num = 49359951418# '&HB7E15163A
LSet a = b

По идее после LSet-а в a.lowD должно быть число &H7E15163A и в a.highD &HB, но в действительности там такие числа
a.lowD = &H17B439A0
a.highD = &H1C0ED
И когда число &H1C0ED17B439A0 преобразовать в десятичную систему то получается 493599514180000.

alibek
Большой Человек
Большой Человек
 
Сообщения: 14205
Зарегистрирован: 19.04.2002 (Пт) 11:40
Откуда: Russia

Сообщение alibek » 05.10.2006 (Чт) 16:51

Верно, Currency это тип данных с фиксированной запятой, четыре знака справа от запятой. Раздели на 10000 и получишь нужное число.
Кстати, inline-объявление для Currency не #, а @.
Lasciate ogni speranza, voi ch'entrate.

Konst_One
Член-корреспондент академии VBStreets
Член-корреспондент академии VBStreets
Аватара пользователя
 
Сообщения: 3041
Зарегистрирован: 09.04.2004 (Пт) 13:47
Откуда: Химки

Сообщение Konst_One » 05.10.2006 (Чт) 16:52

Вообще-то у меня так, если объявить:

Код: Выделить всё
Public Type curUDT
    num As Double
End Type


Код: Выделить всё
?a.lowD
hex( 745799680 )
2C740000

?a.highD
?hex( 1109851178 )
4226FC2A

alibek
Большой Человек
Большой Человек
 
Сообщения: 14205
Зарегистрирован: 19.04.2002 (Пт) 11:40
Откуда: Russia

Сообщение alibek » 05.10.2006 (Чт) 16:54

А зачем Double? В Currency можно не опасаться, что разряды потеряются.
Lasciate ogni speranza, voi ch'entrate.

Mao
Обычный пользователь
Обычный пользователь
Аватара пользователя
 
Сообщения: 95
Зарегистрирован: 10.10.2004 (Вс) 13:09

Сообщение Mao » 05.10.2006 (Чт) 17:02

alibek писал(а):Верно, Currency это тип данных с фиксированной запятой, четыре знака справа от запятой. Раздели на 10000 и получишь нужное число.
Кстати, inline-объявление для Currency не #, а @.

Большое спасибо.

Megas13
Новичок
Новичок
Аватара пользователя
 
Сообщения: 40
Зарегистрирован: 03.08.2006 (Чт) 9:46
Откуда: IL

Re: XOR

Сообщение Megas13 » 13.01.2009 (Вт) 17:16

Позвольте апнуть темку, так как возникла похожая проблема.

Вообщем надо произвести операцию XOR для двух Currency значений.
Следующий код:
Код: Выделить всё
Public Type MYCUR
    lowL As Long
    highL As Long
End Type

Public Function CurencyXor(cur_num As Currency) As Currency
    Dim gg As MYCUR
   
    LSet gg = cur_num
    gg.highL = gg.highL Xor &HAAAAAAAA
    gg.lowL = gg.lowL Xor &HAAAAAAAA
    LSet cur_num = gg
    CurencyXor = cur_num
End Function

создает ошибку "Type mismatch" в строчке:
Код: Выделить всё
LSet gg = cur_num


Я пробовал решить проблему другим способом:
Код: Выделить всё
Private Declare Sub CopyMemory Lib "kernel32" Alias "RtlMoveMemory" (pDst As Any, pSrc As Any, ByVal ByteLen As Long)
Dim number2(7) As Byte

Public Sub InitXor()
    Dim i As Integer
   
    Randomize Timer
    For i = 0 To 7
        number2(i) = Int(Rnd * 255)
    Next
End Sub

Public Function CurrencyXor(cur_num As Currency) As Currency
    Dim number1(7) As Byte
    Dim i As Integer
   
    'Копируем значение в массив
    CopyMemory number1(0), cur_num, 8
   
    For i = 0 To 7
        number1(i) = number1(i) Xor number2(i)
    Next
   
    'Копируем массив обратно в переменную
    CopyMemory cur_num, number1(0), 8
    'Возвращаем значение
    CurrencyXor = cur_num
End Function

Функция InitXor вызывается один раз для создания второго числа в операции XOR, а затем уже вызывается функция CurrencyXor для действия.
Но результат этой операции почемуто получается не верный :( Где я ошибся?
Компьютер не подчиняется законам физики.Только в нем глюки возникают из ничего, файлы исчезают в никуда, а объем измеряется в метрах и называется весом.

След.

Вернуться в Раздел для Профессионалов

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 17

    TopList  
cron