Kirjautuminen

Haku

Tehtävät

Keskustelu: Koodit: VB.NET: Pointteri VB.net:ssä

tnb [15.11.2004 00:25:08]

#

Vaikka pointterit varsinaisesti kuuluvat C-kieleen, on myös VB.net:ssä mahdollisuus pointtereiden käyttöön. Palvelut löytyvät Marshal luokasta, joka sijaitsee System.Runtime.InteropServices:ssä.

Osoittimen tyyppi on IntPtr (Dim a as IntPtr).

GCHandle-luokka mahdollista toisen tavan osoittaa muuttujaa, mutta sijoituslause vain siirtää kohdemuuttujan osoittamaan lähdemuuttujaa ja muutokset näkyvät molemmissa!!

Pointterin käyttö:
- Varataan muistia valvomattomalta alueelta(Unmanaged)
- Sirretään data muistiin
- tehdään jotain ....
- Sirretään data takaisin VB muuttujaan.

Luvuille, teksteille ja rakenteille on omat käskynsä.

Taulukoiden siirtoon on Marshal.Copy, jolla siirto tapahtuu mennen-tullen.

Ohjelma esimerkki ei tee mitään, seuraa muuttujien arvoja debuggerilla niin näet toiminnan erot.

Huom! Jos on pakko tehdä C-kielen kanssa yhteensopivia pointtereita, joita siirretään datana (esim rakenteen sisällä) API funktioille, kannattaa muistin varaus ja pointteri tehdä API:n GlobalAlloc funktiolla.

Imports System.Runtime.InteropServices
Public Structure Point
    Dim x As Integer
    Dim y As Integer
End Structure
Public Class Form1
    Inherits System.Windows.Forms.Form

#Region " Windows Form Designer generated code "

    ' Generoitua Koodia poistettu

#End Region

    Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
        ' tehdään pointteri valvomattomalle muistialueelle,
        ' jonne data siirretään
        ' ja luetaan takaisin
        Dim pointteri As IntPtr
        Dim luku As Integer = 314
        'varataan muistia valvotun koodin ulkopuolelta
        pointteri = Marshal.AllocHGlobal(4) ' integer on 32 bit = 4 tavua
        'kirjoitetaan pointterin osoittamaan muistiin
        Marshal.WriteInt32(pointteri, luku)
        'luetaan takaisin
        Dim toinenLuku As Integer = Marshal.ReadInt32(pointteri)
        '
        'tekstit ja pointteri
        Dim OmaTeksti As String = "Hei siellä"
        Dim ptr As IntPtr = Marshal.StringToHGlobalAuto(OmaTeksti)
        Dim OmaTEksti2 As String = Marshal.PtrToStringAuto(ptr)
        '
        'Struktuurit ja pointteri
        Dim rakenne1, rakenne2 As Point
        rakenne1.x = 100
        rakenne1.y = 200
        Dim ptr2 As IntPtr = Marshal.AllocHGlobal(Marshal.SizeOf(rakenne1))
        Marshal.StructureToPtr(rakenne1, ptr2, True)
        rakenne2 = CType(Marshal.PtrToStructure(ptr2, New Point().GetType), Point) ' Ctype vain koska Option Strict on päällä
        '
        'Osoitin suoraan (samaan)muuttujaan
        Dim gh As GCHandle ' GC = Garbage Collection
        Dim emp(10) As Long : emp(1) = 89765
        gh = GCHandle.Alloc(emp)
        Dim emp2() As Long = CType(gh.Target, Long()) ' Ctype vain koska Option Strict on päällä
        emp2(0) = 111 ' myös emp muuttui!!!!
        gh.Free() 'muistin vapautus
        '
        'Taulukon (1D) osoittaminen valvomattomassa muistissa
        Dim a(10) As Integer : a(6) = 888
        Dim pointteri3 As IntPtr = Marshal.AllocHGlobal(a.Length * 4)
        'kopioidaan a:sta muistiin kohtaan pointteri
        Marshal.Copy(a, 0, pointteri3, a.Length)
        'kopioidaan muistista B:hen
        Dim b(10) As Integer
        Marshal.Copy(pointteri3, b, 0, a.Length)
        b(0) = 99 ' ei vaikuta a:han!!!!!!!!


    End Sub
End Class

Juice [22.11.2004 19:40:52]

#

Kiva, että tämäkin on saatu Putkaan.
Tätä kyllä harvemmin tarvitaan. Jos ruvetaan oikein tarkaksi, niin kielenhuollollisesti parempi olisi "osoitin" eikä pointteri.

Blaze [25.11.2004 12:36:43]

#

Pah, pointteri on oikein hyvä, siitä kaikki tietää heti, mitä tarkotetaan.

T.M. [01.12.2004 20:04:15]

#

Niinpä, kauheeta vinetystä kieliopillisesti oikeista käsitteistä :P

Vastaus

Aihe on jo aika vanha, joten et voi enää vastata siihen.

Tietoa sivustosta