PDA

View Full Version : سوال: تعریف نوع جدید متغییر ؟؟!



سپهر-111
دوشنبه 17 مهر 1391, 15:21 عصر
سلام دوستان:قلب:
ایا امکان داره توی وی بی 6 یک نوع متغییر جدید تعریف کنیم که از 0 تا 65535 باشه ؟؟! (دوبایت بدون علامت)
و فقط اعداد بدون علامت و صحیح رو در خودش قرار بده و با رسیدن به 65535 سریزز بشه ؟؟

ممنون میشم راهنمایی بفرمایید
باتشکر

محسن واژدی
دوشنبه 17 مهر 1391, 19:29 عصر
سلام علیکم
data-typeها (مثل Integer,Double,...) خیر اما UDT (user-defiened-type ها چرا:

Public Type NewUDT
nuFName As String
nuLName As String
nuPhone As Long
End Type

موفق باشید

سپهر-111
دوشنبه 17 مهر 1391, 20:34 عصر
سلام علیکم
data-typeها (مثل Integer,Double,...) خیر اما UDT (user-defiened-type ها چرا:

Public Type NewUDT
nuFName As String
nuLName As String
nuPhone As Long
End Type

موفق باشید


سلام استاد محسن
ممنون که پاسخ دادید
اگه براتون امکان داره ، یک کدبرام بنویسید که بتونم بعنوان یک متغیر دوبایتی ( 0 تا 65535 ) بتونم استفاده کنم
از لطف شما بسیار سپاسگزارم

محسن واژدی
دوشنبه 17 مهر 1391, 21:49 عصر
سلام علیکم
نوع های غیرمنفی را نمیتونیم در vb6 ایجاد کنیم (البته بجز byte)، ولی خب، میتوانیم یک property مشابه نوع Char با طول 0-65535 با همان ویژگی ها (اعداد بدون علامت) ایجاد کنیم
برای مثال اگه property زیر را در ماژول کد قرار بدهیم عملکردی مشابه Char دارد:
Private m_CharVar

Public Property Let CharVar(ByVal vVal)
If Val(vVal) <> vVal Then Err.Raise 13
If Val(vVal) < 0 Or Val(vVal) > 65535 Then Err.Raise 6
m_CharVar = vVal
End Property

Public Property Get CharVar()
CharVar = m_CharVar
End Property


برای مثال:

Private Sub Command1_Click()
On Error GoTo hErr

MsgBox "Test1 : CharVar = 1": CharVar = 1: MsgBox "Test1 - ok", vbInformation 'true
MsgBox "Test2 : CharVar = -1125": CharVar = -1125 'false: raise over-flow error
MsgBox "Test3 : CharVar = 999999": CharVar = 999999 'false: raise over-flow error
MsgBox "Test4 : CharVar = ""any-char""": CharVar = "any-char" 'false: raise mismatch error

Exit Sub

hErr:
MsgBox Err.Number & ": " & Err.Description, vbCritical, "Error"

Resume Next

End Sub


موفق باشید

مهرداد صفا
پنج شنبه 20 مهر 1391, 04:27 صبح
سلام علیکم
نوع های غیرمنفی را نمیتونیم در vb6 ایجاد کنیم (البته بجز byte)، ولی خب، میتوانیم یک property مشابه نوع Char با طول 0-65535 با همان ویژگی ها (اعداد بدون علامت) ایجاد کنیم
برای مثال اگه property زیر را در ماژول کد قرار بدهیم عملکردی مشابه Char دارد:
Private m_CharVar

Public Property Let CharVar(ByVal vVal)
If Val(vVal) <> vVal Then Err.Raise 13
If Val(vVal) < 0 Or Val(vVal) > 65535 Then Err.Raise 6
m_CharVar = vVal
End Property

Public Property Get CharVar()
CharVar = m_CharVar
End Property


برای مثال:

Private Sub Command1_Click()
On Error GoTo hErr

MsgBox "Test1 : CharVar = 1": CharVar = 1: MsgBox "Test1 - ok", vbInformation 'true
MsgBox "Test2 : CharVar = -1125": CharVar = -1125 'false: raise over-flow error
MsgBox "Test3 : CharVar = 999999": CharVar = 999999 'false: raise over-flow error
MsgBox "Test4 : CharVar = ""any-char""": CharVar = "any-char" 'false: raise mismatch error

Exit Sub

hErr:
MsgBox Err.Number & ": " & Err.Description, vbCritical, "Error"

Resume Next

End Sub


موفق باشید
با سلام
البته در این کد m_CharVar اگر از نوع varien باشد 16 بایت و اگر هم از نوع long تعریف شود 4 بایت فضا میگیرد. فکر میکنم منظور دوستمون این بود که برای نگهداری اعداد مثبت کمتر از 2 به توان 16 در دوبایت راهی پیدا کنیم که البته به صورت مستقیم هم نمیشود در vb از این قبیل نوع داده تعریف کرد.
راهی که به ذهن من رسید این بود که در یک کلاس دو متغیر از نوع byte به صورت محلی داشته باشیم و حاصلضرب بایت دوم در 256 را به بایت اول اضافه کنیم و به عنوان مقدار کلاس برگردانیم.
این کد کلاس میشود:

'in the name of god
'صل علی محمد و آله
'class Uint16
Dim byte1 As Byte
Dim byte2 As Byte
Property Get Value() As Long
Value = CLng(byte2) * 256 + byte1
End Property

Property Let Value(NewValue As Long)
If NewValue < 0 Or NewValue >= 2 ^ 16 Then
Err.Raise 6
Else
byte2 = NewValue \ 256
byte1 = NewValue Mod 256
End If
End Property

در این کلاس تنها دو متغیر یک بایتی داریم Property procedure ها هم به خودی خود مقداری را نگهداری نمیکنند که فضایی اشغال کنند.
به عنوان روش دیگر:
همانطور که میدانید در ساختار باینری integer دوبایتی آخرین بیت فقط بیتهای سمت راست خود را ضرب در -1 و منهای -1 میکند یعنی نشاندهنده علامت منفی integer است و از آنجا که اولین بیت نشاندهنده 2 به توان 0 یعنی 1 است آخرین بیت (بیت علامت) برابر 2 به توان 15 (32768) میشود.
پس یک integer علامتدار میتواند عدد مثبتی تا 2^16 (65535) منهای 2^15 (بیت علامت =32768) را در خود نگه دارد.
65535-32768=32767
حالا اگر ما علامت منفی integer را به عنوان +2^15 در نظر بگیریم و این مقدار را با قدر مطلق عدد جمع کنیم یک عدد 16 بیتی مثبت داریم. امیدوارم منظور را منتقل کرده باشم.
در عمل به این صورت است:

'in the name of god
'class UInt16
Dim m_value As Integer
Property Get Value() As Long
If m_value >= 0 Then
Value = m_value
Else
Value = (2 ^ 15) + Abs(m_value)
End If
End Property
Property Let Value(NewValue As Long)
If NewValue < 0 Or NewValue >= 2 ^ 16 Then
Err.Raise 6
Else
If NewValue < 2 ^ 15 Then
m_value = NewValue
Else
m_value = (NewValue - 2 ^ 15) * -1

End If
End If

End Property

که باز هم فقط یک integer دو بایتی در کلاس تعریف شده.
نظر شما چیه آقای واجدی؟

سپهر-111
پنج شنبه 20 مهر 1391, 08:50 صبح
با سلام
البته در این کد m_CharVar اگر از نوع varien باشد 16 بایت و اگر هم از نوع long تعریف شود 4 بایت فضا میگیرد. فکر میکنم منظور دوستمون این بود که برای نگهداری اعداد مثبت کمتر از 2 به توان 16 در دوبایت راهی پیدا کنیم که البته به صورت مستقیم هم نمیشود در vb از این قبیل نوع داده تعریف کرد.
راهی که به ذهن من رسید این بود که در یک کلاس دو متغیر از نوع byte به صورت محلی داشته باشیم و حاصلضرب بایت دوم در 256 را به بایت اول اضافه کنیم و به عنوان مقدار کلاس برگردانیم.
این کد کلاس میشود:

'in the name of god
'صل علی محمد و آله
'class Uint16
Dim byte1 As Byte
Dim byte2 As Byte
Property Get Value() As Long
Value = CLng(byte2) * 256 + byte1
End Property

Property Let Value(NewValue As Long)
If NewValue < 0 Or NewValue >= 2 ^ 16 Then
Err.Raise 6
Else
byte2 = NewValue \ 256
byte1 = NewValue Mod 256
End If
End Property

در این کلاس تنها دو متغیر یک بایتی داریم Property procedure ها هم به خودی خود مقداری را نگهداری نمیکنند که فضایی اشغال کنند.
به عنوان روش دیگر:
همانطور که میدانید در ساختار باینری integer دوبایتی آخرین بیت فقط بیتهای سمت راست خود را ضرب در -1 و منهای -1 میکند یعنی نشاندهنده علامت منفی integer است و از آنجا که اولین بیت نشاندهنده 2 به توان 0 یعنی 1 است آخرین بیت (بیت علامت) برابر 2 به توان 15 (32768) میشود.
پس یک integer علامتدار میتواند عدد مثبتی تا 2^16 (65535) منهای 2^15 (بیت علامت =32768) را در خود نگه دارد.
65535-32768=32767
حالا اگر ما علامت منفی integer را به عنوان +2^15 در نظر بگیریم و این مقدار را با قدر مطلق عدد جمع کنیم یک عدد 16 بیتی مثبت داریم. امیدوارم منظور را منتقل کرده باشم.
در عمل به این صورت است:

'in the name of god
'class UInt16
Dim m_value As Integer
Property Get Value() As Long
If m_value >= 0 Then
Value = m_value
Else
Value = (2 ^ 15) + Abs(m_value)
End If
End Property
Property Let Value(NewValue As Long)
If NewValue < 0 Or NewValue >= 2 ^ 16 Then
Err.Raise 6
Else
If NewValue < 2 ^ 15 Then
m_value = NewValue
Else
m_value = (NewValue - 2 ^ 15) * -1

End If
End If

End Property

که باز هم فقط یک integer دو بایتی در کلاس تعریف شده.
نظر شما چیه آقای واجدی؟


سلام
باتشکر از راهنمایی و پاسخ شما دوست عزیز
ولی اینجوری هم باز چهار بایت فضا اشغال میکنه
من میخواستم دقیقا مثل integer باشه و فقط دوبایت اشغال کنه ولی بدون علامت باشه ( 0 تا 65535 )

محسن واژدی
پنج شنبه 20 مهر 1391, 16:36 عصر
من میخواستم دقیقا مثل integer باشه و فقط دوبایت اشغال کنه ولی بدون علامت باشه ( 0 تا 65535 )
سلام علیکم
بجز Byte که یک بایت است مابقی از 4 بایت به بالا هستند، در صورت لزوم میتوانید نوع کد پست4# را به Long با 4بایت تغییر بدین

موفق باشید

سپهر-111
پنج شنبه 20 مهر 1391, 21:51 عصر
سلام علیکم
بجز Byte که یک بایت است مابقی از 4 بایت به بالا هستند، در صورت لزوم میتوانید نوع کد پست4# را به Long با 4بایت تغییر بدین

موفق باشید
سلام استاد محسن
با تشکر از پاسخ شما
بله متاسفانه تو ویژوال بیسیک نمیشه به همچین متغیری دسترسی داشت و خودش یه نوع ضعف هستش
و مجبور شدم به یک نوع دیگه نیاز خودم برطرف کنم
بیشترین ضعفی که توی وی بی دیدم همین کار با بیتها و بایتهای بدون علامت بوده است