speed of populating listview using mysql in vb.net - mysql

This is my code for populating the listview:
Dim itms As ListViewItem
Dim itm As New List(Of ListViewItem)
Dim itemcoll(2) As String
Dim strQ As String = String.Empty
strQ = "SELECT COLOR_CODE,DESC from COLORS"
cmd = New MySqlCommand(strQ, con)
Try
con.Open()
rs = cmd.ExecuteReader
lstview.Items.Clear()
Application.DoEvents()
lstview.SuspendLayout()
lstview.BeginUpdate()
lstview.Visible = False
While rs.Read
itemcoll(0) = IIf(Not IsDBNull(rs.Item("COLOR_CODE")), rs.Item("COLOR_CODE"), 0)
itemcoll(1) = IIf(Not IsDBNull(rs.Item("DESC")), rs.Item("DESC"), 0)
itms = New ListViewItem(itemcoll)
'lstview.Items.Add(itms)
itm.Add(itms)
End While
rs.Close()
lstview.Items.AddRange(itm.ToArray)
lstview.EndUpdate()
lstview.Visible = True
lstview.ResumeLayout()
Catch ex As Exception
MsgBox(ex.Message)
Finally
con.Close()
End Try
This code is fast for populating rows of 10,000+, but If I am populating more than 50, 000, it is slow, it take 2 seconds to populate the listview, is the speed normal or slow?
And also what are the other techniques to speed up populating? I have use some of the ways to increase the speep of populating.
Thanks for the help.

Try this sample. Sometimes unnecessarily writing to placeholder variables can slow performance, though theoretically not much should be different in execution time.
Dim itm As New List(Of ListViewItem)
Dim strQ As String = "SELECT COLOR_CODE,DESC from COLORS"
cmd = New MySqlCommand(strQ, con)
lstview.Items.Clear()
Application.DoEvents()
lstview.SuspendLayout()
lstview.BeginUpdate()
lstview.Visible = False
Try
con.Open()
rs = cmd.ExecuteReader
While rs.Read
itm.Add(New ListViewItem({Convert.ToString(rs.Item("COLOR_CODE")),
Convert.ToString(rs.Item("DESC"))}))
End While
Catch ex As Exception
MsgBox(ex.Message)
Finally
con.Close()
lstview.Items.AddRange(itm)
lstview.EndUpdate()
lstview.Visible = True
lstview.ResumeLayout()
End Try

Related

There is already an open Data Reader associated with this connection which must be closed first vb.net.vb

Dim Conn As MySqlConnection
Dim Command As MySqlCommand
Dim Reader As MySqlDataReader
Dim server As String = "serverxxxxxxxx.1;user=root;database=xxxxxxxxx"
Public Sub testing()
Conn = New MySqlConnection
Conn.ConnectionString = server
Dim datecompare As String = Date.Today.ToString("yyyy-MM-dd hh:mm:ss")
Dim primarykey1 As String = ""
Dim primarykey2 As String = ""
Try
If Not Conn.State = ConnectionState.Open Then
Conn.Open()
End If
Dim Query1 As String
Query1 = "Select * From `tblborrow` Where `DueDate` = '" & datecompare & "'"
Command = New MySqlCommand(Query1, Conn)
Reader = Command.ExecuteReader
While Reader.Read
primarykey1 = Reader.GetInt32("BorrowID")
Try
If Not Conn.State = ConnectionState.Open Then
Conn.Open()
End If
Dim query2 As String
query2 = "Update `tblborrow` Set `Remarks` = '" & "Due Date" & "' Where `BorrowID` = '" & primarykey1 & "'"
Command = New MySqlCommand(query2, Conn)
Reader = Command.ExecuteReader
Reader.Close()
Conn.Close()
Catch ex As Exception
MsgBox(ex.Message)
End Try
'end of duedate
End While
Reader.Close()
Conn.Close()
Catch ex As Exception
MsgBox(ex.Message)
End Try
'for OVER DUE
Try
If Not Conn.State = ConnectionState.Open Then
Conn.Open()
End If
Dim Query1 As String
Query1 = "Select * From `tblborrow` Where `DueDate` < '" & datecompare & "'"
Command = New MySqlCommand(Query1, Conn)
Reader = Command.ExecuteReader
While Reader.Read
primarykey2 = Reader.GetInt32("BorrowID")
Try
If Not Conn.State = ConnectionState.Open Then
Conn.Open()
End If
Dim query2 As String
query2 = "Update `tblborrow` Set `Remarks` = '" & "Over Due" & "' Where `BorrowID` = '" & primarykey2 & "'"
Command = New MySqlCommand(query2, Conn)
Reader = Command.ExecuteReader
Reader.Close()
Conn.Close()
Catch ex As Exception
MsgBox(ex.Message)
End Try
'end of Over Due
End While
Reader.Close()
Conn.Close()
Catch ex As Exception
MsgBox(ex.Message)
End Try
End Sub
Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
Call testing()
End Sub
I created a public sub that will select and update the Remarks in my database based on the borrowID(this is auto increment). The save date in DueDate and compare i declare with the current time today, but every time i click the button where i saved the code i get this error There is already an openDataReaderassociated with this connection which must be closed first
i double checked my code and didn't miss to put reader.close() after every conn.close() or i don't know maybe i missed..
i tried some several changes in my code but still i get the same error.
can some help me and build my code? .. thanks.
Try to use different variable for the readers, maybe Reader1 and Reader2.
It's probably because you used the same reader to execute different query hence the already open datareader error.
You try to open the same book which is already open. At least make it a different book.
You are attempting to open 2 readers on a single connection. See the double headed arrows.
Reader = Command.ExecuteReader'<<----
While Reader.Read
primarykey1 = Reader.GetInt32("BorrowID")
Try
If Not Conn.State = ConnectionState.Open Then
Conn.Open()
End If
Dim query2 As String
query2 = "Update `tblborrow` Set `Remarks` = '" & "Due Date" & "' Where `BorrowID` = '" & primarykey1 & "'"
Command = New MySqlCommand(query2, Conn)
Reader = Command.ExecuteReader '<<----
If you break your code into logical units with only a single thing happening in each method it is a bit easier to see where things go wrong.
Keeping your database objects local to the methods where they are used allows you to be sure they are closed and disposed. Using...End Using blocks handle this for you even if there is an error.
Notice, in the 2 Update methods, the parameters are added outside the For loop and only the value that changes is set inside the loop.
Dim ConString As String = "serverxxxxxxxx.1;user=root;database=xxxxxxxxx"
Public Sub GetPKs()
Dim pkList As New List(Of Integer)
Dim DueDate As String = Date.Today.ToString("yyyy-MM-dd hh:mm:ss")
Using Conn As New MySqlConnection(ConString),
cmd As New MySqlCommand("Select BorrowID From tblborrow Where DueDate = #DueDate")
cmd.Parameters.Add("#DueDate", MySqlDbType.VarChar, 100).Value = DueDate
Conn.Open()
Using reader As MySqlDataReader = cmd.ExecuteReader
While reader.Read
pkList.Add(reader.GetInt32("BorrowID"))
End While
End Using
End Using
UpdateRemarks(pkList, DueDate)
End Sub
Private Sub UpdateRemarks(pks As List(Of Integer), DueDate As String)
Using con As New MySqlConnection(ConString),
cmd As New MySqlCommand("Update tblborrow Set Remarks = #DueDate Where BorrowID = #PK", con)
With cmd.Parameters
.Add("#DueDate", MySqlDbType.VarChar, 100).Value = DueDate
.Add("#PK", MySqlDbType.Int32)
End With
con.Open()
For Each i In pks
cmd.Parameters("#PK").Value = i
cmd.ExecuteNonQuery()
Next
End Using
End Sub
Private Sub GetOverduePKs()
Dim pkList As New List(Of Integer)
Using cn As New MySqlConnection(ConString),
cmd As New MySqlCommand("Select BorrowID From tblborrow Where DueDate < #DueDate")
cmd.Parameters.Add("#DueDate", MySqlDbType.VarChar, 100).Value = Date.Today.ToString("yyyy-MM-dd hh:mm:ss")
cn.Open()
Using reader = cmd.ExecuteReader
While reader.Read
pkList.Add(reader.GetInt32("BorrowID"))
End While
End Using
End Using
UpdateOverdueRemarks(pkList)
End Sub
Private Sub UpdateOverdueRemarks(pks As List(Of Integer))
Using cn As New MySqlConnection(ConString),
cmd As New MySqlCommand("Update tblborrow Set Remarks = 'Over Due' Where BorrowID = #PK")
cmd.Parameters.Add("#PK", MySqlDbType.Int32)
cn.Open()
For Each i In pks
cmd.Parameters("#PK").Value = i
cmd.ExecuteNonQuery()
Next
End Using
End Sub
Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
GetPKs()
GetOverduePKs()
End Sub
use 2 connections CONN and CONN2, with the same parameters, use CONN to open the QUERY1 reader. While reading, use CONN2 to create the 2nd query. Note that this works for MySQL. MS-Access can handle multiple commands in one connection, MySql cannot and needs separate connections. Sqlite cannot handle 2 simultanuos connections. there you have to use in incore temporary array or list. From a working program:
Dim DbConn As New MySqlConnection(SqlProv)
Dim DbConn2 As New MySqlConnection(SqlProv)
-
Dim SQLsfSelect As String = "SELECT CollSeq FROM ToBeIndexed WHERE CollCode = #CollCode"
Dim DRsfSelect As MySqlDataReader = Nothing
Dim DCsfSelect As MySqlCommand
Dim sfSelP1 As New MySqlParameter("#CollCode", MySqlDbType.VarChar, 4)
DCsfSelect = New MySqlCommand(SQLsfSelect, DbConn)
-
Dim SQLasSelect As String = "SELECT DISTINCT CollSeq FROM Data WHERE CollCode = #CollCode ORDER BY CollSeq"
Dim DRasSelect As MySqlDataReader = Nothing
Dim DCasSelect As MySqlCommand
Dim asSelP1 As New MySqlParameter("#CollCode", MySqlDbType.VarChar, 4)
DCasSelect = New MySqlCommand(SQLasSelect, DbConn2)
-
DbConn.Open()
sfSelP1.Value = CurCollCode
CollSeqToIdxC.Clear()
Try
DRsfSelect = DCsfSelect.ExecuteReader()
Do While (DRsfSelect.Read())
CollSeq = GetDbIntegerValue(DRsfSelect, 0)
DbConn2.Open()
asSelP1.Value = CurCollCode
Try
DRasSelect = DCasSelect.ExecuteReader()
Do While (DRasSelect.Read())
CollSeq = GetDbIntegerValue(DRasSelect, 0)
CollSeqToIdxC.Add(CollSeq, CStr(CollSeq))
Loop
Catch ex As Exception
MsgBox(ex.ToString(), , SysMsg1p(402, CurCollCode))
Finally
If Not (DRasSelect Is Nothing) Then
DRasSelect.Close()
End If
End Try
DbConn2.Close()
Loop
Catch ex As Exception
MsgBox(ex.ToString(), , SysMsg1p(403, CurCollCode))
Finally
If Not (DRsfSelect Is Nothing) Then
DRsfSelect.Close()
End If
End Try
DbConn.Close()

VB.Net Delete Selected Row in DataGridView MySql

This the code that I use. The message box is appearing but when I select yes, the selected row is not deleted at the datagridview and database.
Private Sub Delete2_Click_1(sender As Object, e As EventArgs) Handles Delete2.Click
MySqlConn = New MySqlConnection
MySqlConn.ConnectionString = "server=127.0.0.1;userid=root;password=;database=equipment"
Try
If Me.DataGridView2.Rows.Count > 0 Then
If Me.DataGridView2.SelectedRows.Count > 0 Then
Dim intStdID As Char = Me.DataGridView2.SelectedRows(0).Cells("asset_code").Value
'open connection
If Not MySqlConn.State = ConnectionState.Open Then
MySqlConn.Open()
End If
'delete data
Dim cmd As New MySqlCommand
cmd.Connection = MySqlConn
cmd.CommandText = "DELETE * FROM equipment.equipment" & intStdID
Dim res As DialogResult
res = MsgBox("Are you sure you want to DELETE the selected Row?", MessageBoxButtons.YesNo)
If res = Windows.Forms.DialogResult.Yes Then
cmd.ExecuteNonQuery()
Else : Exit Sub
End If
'refresh data
Load_table()
'close connection
MySqlConn.Close()
End If
End If
Catch ex As MySqlException
End Try
Look at this line:
cmd.CommandText = "DELETE * FROM equipment.equipment" & intStdID
It attempts to append the ID value from the selected cell to the SQL statement. However, it seems like this is just the ID value. You also need the WHERE ID= portion for the query.
Moreover, it's using this ID value in the query in the wrong way. It's NEVER okay to use string concatenation to include data in a query. You must use parameterized queries.
The code below demonstrates this, as well as several other better patterns for this method, with the caveat that I had to guess as some names and types from your database.
Private Sub Delete2_Click_1(sender As Object, e As EventArgs) Handles Delete2.Click
If Me.DataGridView2.Rows.Count = 0 OrElse Me.DataGridView2.SelectedRows.Count = 0 Then
Exit Sub
End If
Dim res As DialogResult = MsgBox("Are you sure you want to DELETE the selected Row?", MessageBoxButtons.YesNo)
If res <> DialogResult.Yes Then Exit Sub
Dim intStdID As Char = Me.DataGridView2.SelectedRows(0).Cells("asset_code").Value
Dim SQL as String = "DELETE * FROM equipment.equipment WHERE equipment.StdID= #AssetCode"
Using con As New MySqlConnection("server=127.0.0.1;userid=root;password=;database=equipment"), _
cmd As New MySqlCommand(SQL, con)
cmd.Parameters.Add("#AssetCode", MySqlDbType.VarChar, 1).Value = intStdID
con.Open()
cmd.ExecuteNonQuery()
End Using
Load_table()
End Sub

vb.net sql date index was outside the bounds of the array

This code seems strange for me because it doesn't have arrays yet it says "index was outside the bounds of the array". Anyways, here's my code
con.Open()
'sql problem
Try
sql ="SELECT trans_event FROM tbl_transdetail WHERE trans_fromdate = #2015-08-16#"
com = New MySqlCommand(sql, con)
reader = com.ExecuteReader
If reader.HasRows Then
While reader.Read()
Dim ev = reader.GetString("trans_event")
Dim lo = reader.GetString("trans_location")
Dim frmd As Date = reader.GetString("trans_fromdate")
Dim frmt = reader.GetString("trans_fromtime")
Dim tod As Date = reader.GetString("trans_todate")
Dim tot = reader.GetString("trans_totime")
.Items.Add(New ListViewItem({ev, lo, frmd, frmt, tod, tot}))
End While
Else
Dim i = reader.FieldCount
End If
reader.Close()
Catch ex As Exception
MessageBox.Show(ex.Message)
End Try
where the error is shockingly on the sql statement..
any help will greatly appreciated... thanks...

vb.net/mysql show more then 1 row in TextBox

I just started messing around with Visual basic (vb.net) and am trying to show more then 1 database row in a TextBox, so far I have this:
Private Sub foobox_Load(sender As System.Object, e As System.EventArgs) Handles MyBase.Load
Dim conn As MySqlConnection
conn = New MySqlConnection
conn.ConnectionString = connStr
Try
conn.Open()
Catch myerror As MySqlException
MsgBox("No connection")
End Try
Dim myAdaptor As New MySqlDataAdapter
Dim sqlquery = "SELECT * FROM foo ORDER BY id DESC"
Dim myCommand As New MySqlCommand()
myCommand.Connection = conn
myCommand.CommandText = sqlquery
myAdaptor.SelectCommand = myCommand
Dim myData As MySqlDataReader
myData = myCommand.ExecuteReader()
If myData.HasRows Then
myData.Read()
Viewer.Text = myData("foo1") & myData("foo2")
End If
myData.Close()
conn.Close()
End Sub
which connects to a database successfully but but it only outputs 1 row, how can I get it to output more?
You need a loop reading data and storing line after line in a StringBuilder.
Then, when exiting from the reading loop set the Text property of your textbox
Dim sb as StringBuilder = new StringBuilder()
While myData.Read()
sb.AppendLine(myData("foo1") & myData("foo2"))
End While
Viewer.Text = sb.ToString
and, of course, your textbox should have the MultiLine property set to True
Apart from this direct answer to your question, your code should be changed to dispose the connection and the datareader after use, I have also removed the DataAdapter because is not needed here
Using conn = New MySqlConnection(connStr)
Try
conn.Open()
Catch myerror As MySqlException
MsgBox("No connection")
End Try
Dim sqlquery = "SELECT * FROM foo ORDER BY id DESC"
Dim myCommand As New SqlCommand(sqlquery, conn)
Using myData = myCommand.ExecuteReader()
Dim sb as StringBuilder = new StringBuilder()
While myData.Read()
sb.AppendLine(myData("foo1") & myData("foo2"))
End While
Viewer.Text = sb.ToString
End Using
End Using
You need some kind of loop. I would also use the Using statement to ensure that all unmanaged resources are disposed even in case of an exception(it also closes the connection):
Using conn As New MySqlConnection(connStr)
Using myCommand As New MySqlCommand("SELECT * FROM foo ORDER BY id DESC", conn)
Try
conn.Open()
Using myData = myCommand.ExecuteReader()
If myData.HasRows Then
While myData.Read()
Dim line = String.Format("{0}{1}{2}",
myData.GetString(myData.GetOrdinal("foo1")),
myData.GetString(myData.GetOrdinal("foo1")),
Environment.NewLine)
viewer.Text &= line
End While
End If
End Using
Catch ex As Exception
MessageBox.Show(ex.ToString())
End Try
End Using
End Using
However, if you want to show multiple records i would recommend a ListBox instead. It's more efficient with many items and it also separates them logical from each other.
( just replace viewer.Text &= line with ListBox1.Items.Add(line) )

data reader in vb.net

Please help, how do I make a while loop equivalent of this for loop. So that I could read from one row in the table of mysql database and display it on the combobox in vb.net.
I use this code, but its definitely not useful if there are 3 or more items that are added in the row:
Dim i As Integer
Dim rdr As Odbc.OdbcDataReader
rdr = con.readfrom_drug_type_table()
For i = 0 To 1
If rdr.HasRows = True Then
rdr.Read()
ComboBox2.Items.Add(rdr("Drug_type"))
End If
Next i
I want to read all the data from that the Drug_type row
Please help, thanks
If you want to read only first row than just use
If rdr.Read() Then
ComboBox2.Items.Add(rdr("Drug_type"))
End If
Update
Try
myConnection = New SqlConnection("server=localhost;uid=sa;pwd=;database=pubs")
'you need to provide password for sql server
myConnection.Open()
myCommand = New SqlCommand("Select * from discounts", myConnection)
dr = myCommand.ExecuteReader
While dr.Read()
WriteLine(dr(0))
WriteLine(dr(1))
WriteLine(dr(2))
WriteLine(dr(3))
WriteLine(dr(4))
' writing to console
End While
Catch
End Try
dr.Close()
myConnection.Close()
#pranay
You don't need the nested loops.
Try
myConnection = New SqlConnection("server=localhost;uid=sa;pwd=;database=pubs")
myConnection.Open()
myCommand = New SqlCommand("Select * from discounts", myConnection)
dr = myCommand.ExecuteReader()
While dr.Read()
WriteLine(dr(0))
WriteLine(dr(1))
WriteLine(dr(2))
WriteLine(dr(3))
WriteLine(dr(4))
End While
dr.Close()
Finally
myConnection.Close()
End Try