DateTime.Now value is changing - vb.net

I'm trying to use the a current timestamp as an identifier for some data.
Executing the following code will result in a different timestamp (+50ms )with each execution even though timestamp is assigned before the For Each
Dim timestamp = DateTime.Now
For Each x In y
System.Threading.Thread.Sleep(50)
Foo(data, timestamp)
Next
Sub Foo(data As Dat, timestamp As Date)
Dim con As New SqlConnection
con.ConnectionString = ConfigurationManager.ConnectionStrings("TopSecret").ConnectionString
Dim cmd As SqlCommand = con.CreateCommand
con.Open()
cmd.CommandType = CommandType.StoredProcedure
cmd.CommandText = "spX"
cmd.Parameters.Add(New SqlParameter("#Data", data))
cmd.Parameters.Add(New SqlParameter("#Timestamp", timestamp))
cmd.ExecuteNonQuery()
End Sub
But 2nd snippet below will print the identical time every time - and I believe that's the documented behavior.
Why does it behave different here?
Dim timestamp = DateTime.Now
For i As Integer = 0 To 3
str += timestamp .ToString + vbNewLine
Threading.Thread.Sleep(1000)
Next

Related

The problem is conversion from string to type date is not valid

Option Explicit On
Imports System.Data.OleDb
Public Class Form1
Dim objCon As New OleDbConnection
Dim strSQL As String
Dim strConnect As String = "Provider= Microsoft.ACE.OLEDB.12.0;Data Source=C:\Users\Abry\Documents\Bilik.accdb"
Dim da As New OleDb.OleDbDataAdapter
Dim ds As New DataSet
Private Sub TempahButton_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles TempahButton.Click
Dim startDate As String = DateTimePicker1.Value.ToString("dd/MM/yyyy")
Dim str As String
startDate = DateTimePicker1.Value
objCon.ConnectionString = strConnect
objCon.Open()
str = "Insert into bilik(Bilik, Tujuan, [Masa Masuk], [Masa Keluar]) values(?, ?, ?, ?)"
str = "Insert into bilik(Tarikh) values(startDate = DateTimePicker1.Value.ToShortDateString)"
Dim cmd As OleDbCommand = New OleDbCommand(str, objCon)
cmd.Parameters.Add(New OleDbParameter("Bilik", CType(BilikComboBox.SelectedIndex, String)))
cmd.Parameters.Add(New OleDbParameter("Tujuan", CType(TujuanTextBox.Text, String)))
cmd.Parameters.Add(New OleDbParameter("Tarikh", CType(DateTimePicker1.Value, Date)))
cmd.Parameters.Add(New OleDbParameter("Masa Masuk", CType(MasaMasukMaskedTextBox.Text, String)))
cmd.Parameters.Add(New OleDbParameter("Masa Keluar", CType(MasaKeluarMaskedTextBox.Text, String)))
Try
cmd.ExecuteNonQuery()
cmd.Dispose()
objCon.Close()
TujuanTextBox.Clear()
BilikComboBox.Text = ""
DateTimePicker1.Value = ""
MasaMasukMaskedTextBox.Clear()
MasaKeluarMaskedTextBox.Clear()
Catch ex As Exception
MsgBox(ex.Message)
End Try
End Sub
End Class
Tarikh is date declare
Conversion from string to type date is not valid
The issue is, apparently, here:
DateTimePicker1.Value = ""
That means that everything else you posted is irrelevant. The issue is, as the error message clearly states, it is not valid to assign an empty String to a property that is type Date.
The Value property of a DateTimePicker is type Date and so you must assign a Date value to it. There's no such thing as an empty Date so you must either assign a default date, e.g. today's date:
DateTimePicker1.Value = Date.Today
or you need to use the functionality built into the DateTimePicker control to indicate that no date is selected. If you want to know how a DateTimePicker control works, read the class documentation.

how to use date in where clause to search data from access data base in vb.net?

i want to search data from my data base using date in where clause.
But i am getting an error while executing the code.
I am trying this code.
Sub comboboxSELECTED()
Dim a As Date
Form1.ComboBox1.Text = a
Dim con As New OleDb.OleDbConnection
con.ConnectionString = "Provider=Microsoft.ACE.OLEDB.12.0;Data Source=Mdm.accdb"
con.Open()
Dim q As String = "select * from Rice Where DateReceived =" & Form1.ComboBox1.SelectedText
Dim cmd As New OleDb.OleDbCommand(q, con)
Dim Reader As OleDb.OleDbDataReader = cmd.ExecuteReader
While Reader.Read
Form1.ListView1.Items.Add(Reader(0))
Form1.ListView1.Items(Form1.ListView1.Items.Count - 1).SubItems.Add(Reader(1))
Form1.ListView1.Items(Form1.ListView1.Items.Count - 1).SubItems.Add(Reader(2))
Form1.ListView1.Items(Form1.ListView1.Items.Count - 1).SubItems.Add(Reader(3))
Form1.ListView1.Items(Form1.ListView1.Items.Count - 1).SubItems.Add(Reader(4))
Form1.ListView1.Items(Form1.ListView1.Items.Count - 1).SubItems.Add(Reader(5))
Form1.ListView1.Items(Form1.ListView1.Items.Count - 1).SubItems.Add(Reader(6))
Form1.ListView1.Items(Form1.ListView1.Items.Count - 1).SubItems.Add(Reader(7))
Form1.DateTimePicker1.Text = Reader("DateReceived")
Form1.TxtEnrolment.Text = Reader("Enrolment")
Form1.TxtReceived.Text = Reader("QtyReceived")
Form1.TxtTotal.Text = Reader("TotalQuantity")
Form1.TxtUtilised.Text = Reader("QtyUtilised")
Form1.TxtBalance.Text = Reader("Balance")
End While
Reader.Close()
con.Close()
End Sub
Please try changing that section of code to this:
String q = "select * from Rice Where DateReceived = #datercvd";
OleDb.OleDbCommand cmd = New OleDb.OleDbCommand(q, con);
OleDbParameter objectdate = new OleDbParameter("#datercvd", OleDbType.DBDate);
objectdate.Value = Convert.ToDateTime(Form1.ComboBox1.SelectedText);
cmd.Parameters.Add(objectdate);
It does a match on the date, converts from a string, and takes care of SQL injection isues.
The VB.net code...
Private Sub ComboBoxSelected()
Using con As New OleDb.OleDbConnection
con.ConnectionString = "Provider=Microsoft.ACE.OLEDB.12.0;Data Source=Mdm.accdb"
Dim q As String = "Select * from Rice Where DateReceived =#DateReceived"
Using cmd As New OleDb.OleDbCommand(q, con)
cmd.Parameters.Add("#DateReceived", OleDbType.Date).Value = CDate(Form1.ComboBox1.SelectedText)
con.Open()
Using Reader As OleDb.OleDbDataReader = cmd.ExecuteReader
While Reader.Read
'Your code
End While
End Using
End Using
End Using
End Sub

if the input value is in between two values then display the result

I have a SQL table with three columns "From","To" and "Equivalent Value". Each value is shown below:
From To Equivalent Value
1,001.00 2,000.00 200.00
2,001.00 3,000.00 300.00
Now if the user enters the value "1,200.00" in textbox1 it will display the result value to textbox2 which is "200.00" because that is the corresponding value of between "From" and "To.
Another condition, if the user enters the value "2,500.00" in textbox1 it will display the value "300.00".
So far, I have tried this code but no luck:
Dim conn As SqlConnection = SQLConn()
Dim da As New SqlDataAdapter
Dim dt As New DataTable
conn.Open()
Dim cmd As New SqlCommand("", conn)
Dim result As String
cmd.CommandText = "SELECT [Equivalent Value] FROM tblSSS"
result = IIf(IsDBNull(cmd.ExecuteScalar), "", cmd.ExecuteScalar)
da.SelectCommand = cmd
dt.Clear()
da.Fill(dt)
If result <> "" Then
If TextBox1.Text >= dt.Rows(0)(1).ToString() And TextBox1.Text <= dt.Rows(0)(2).ToString() Then
TextBox2.Text = dt.Rows(0)(3).ToString()
End If
End If
If I have got this right I think there are a couple of things I would change which may help you:
Use Using. This will dispose of the SQL objects once finished with.
Use SqlParameters. This will help with filtering your data.
Remove the use of SqlDataAdapter. In this case I don't feel it's needed.
The use of IIf. I will be using If which has replaced IIf.
With these in mind I would look at something like this:
Dim fromValue As Decimal = 0D
Dim toValue As Decimal = 0D
If Decimal.TryParse(TextBox1.Text, fromValue) AndAlso Decimal.TryParse(TextBox1.Text, toValue) Then
Dim dt As New DataTable
Using conn As SqlConnection = SQLConn,
cmd As New SqlCommand("SELECT [Equivalent Value] FROM tblSSS WHERE [From] >= #From AND [To] <= #To", conn)
cmd.Parameters.Add(New SqlParameter With {.ParameterName = "#From", .SqlDbType = SqlDbType.Decimal, .Value = fromValue})
cmd.Parameters.Add(New SqlParameter With {.ParameterName = "#To", .SqlDbType = SqlDbType.Decimal, .Value = toValue})
conn.Open()
dt.Load(cmd.ExecuteReader)
End Using
If dt.Rows.Count = 1 Then
TextBox2.Text = If(IsDBNull(dt.Rows(0).Item("Equivalent Value")), "0", dt.Rows(0).Item("Equivalent Value").ToString)
End If
End If
Note the use of Decimal.TryParse:
Converts the string representation of a number to its Decimal equivalent. A return value indicates whether the conversion succeeded or failed.
This is an assumption that the From and To fields in your database are Decimal.
Now to explain the difference between IIf and If. IIf executes each portion of the statement even if it's true whilst If executes only one portion. I won't go into detail as many others on here have done that already. Have a look at this answer.
As per Andrew Morton's comment and more in line with what the OP attempted here is a solution that uses ExecuteScaler.
ExecuteScaler executes the query, and returns the first column of the first row in the result set returned by the query. Additional columns or rows are ignored.
With this in mind:
'I reset the value of TextBox2.Text. You may not want to.
TextBox2.Text = ""
Dim fromValue As Decimal = 0D
Dim toValue As Decimal = 0D
If Decimal.TryParse(TextBox1.Text, fromValue) AndAlso Decimal.TryParse(TextBox1.Text, toValue) Then
Using conn As SqlConnection = SQLConn,
cmd As New SqlCommand("SELECT [Equivalent Value] FROM tblSSS WHERE [From] >= #From AND [To] <= #To", conn)
cmd.Parameters.Add(New SqlParameter With {.ParameterName = "#From", .SqlDbType = SqlDbType.Decimal, .Value = fromValue})
cmd.Parameters.Add(New SqlParameter With {.ParameterName = "#To", .SqlDbType = SqlDbType.Decimal, .Value = toValue})
conn.Open()
Try
TextBox2.Text = cmd.ExecuteScalar().ToString()
Catch ex As Exception
End Try
End Using
End If
I have used the example on the ExecuteScaler MSDN documentation. You might want to look into handling the exception on the Try Catch a little better and not letting it go to waste.
You may want to place this code on the TextBox1.Leave method or maybe on a Button.Click method. That's totally up to you.
There may a few changes you may need to make however I think this will give you a few ideas on how to move ahead with your code.
Hope it Helps...
Dim connetionString As String
Dim cnn As SqlConnection
Dim cmd As SqlCommand
Dim sql As String
connetionString = "Data Source=ServerName;Initial Catalog=DatabaseName;User ID=UserName;Password=Password"
sql = "SELECT [Equivalent Value] FROM tblSSS WHERE [FROM]<=" & Val(TextBox1.Text) & " AND [TO]>= " & Val(TextBox1.Text)
cnn = New SqlConnection(connetionString)
Try
cnn.Open()
cmd = New SqlCommand(sql, cnn)
Dim count As Int32 = Convert.ToInt32(cmd.ExecuteScalar())
cmd.Dispose()
cnn.Close()
Catch ex As Exception
MsgBox("Can not open connection ! ")
End Try

How can I read a specific column in a database?

I hava a Table named DTR_Table it has 8 columns in it namely:
EmployeeID,Date,MorningTime-In,MorningTime-Out,AfternoonTime-In,AfternoonTime-Out,UnderTime,Time-Rendered.I want to read the column "AfternoonTime-In".
Following is my code. It reads my "AfternoonTime-In" field, but it keeps on displaying "Has Rows" even if there is nothing in that column.
How can I fix this?
Connect = New SqlConnection(ConnectionString)
Connect.Open()
Dim Query1 As String = "Select [AfternoonTime-Out] From Table_DTR Where Date = #Date and EmployeeID = #EmpID "
Dim cmd1 As SqlCommand = New SqlCommand(Query1, Connect)
cmd1.Parameters.AddWithValue("#Date", DTRform.datetoday.Text)
cmd1.Parameters.AddWithValue("#EmpID", DTRform.DTRempID.Text)
Using Reader As SqlDataReader = cmd1.ExecuteReader()
If Reader.HasRows Then
MsgBox("Has rows")
Reader.Close()
Else
MsgBox("empty")
End If
End Using`
After returning the DataReader you need to start reading from it if you want to extract values from your query.
Dim dt = Convert.ToDateTime(DTRform.datetoday.Text)
Dim id = Convert.ToInt32(DTRform.DTRempID.Text)
Using Connect = New SqlConnection(ConnectionString)
Connect.Open()
Dim Query1 As String = "Select [AfternoonTime-Out] From Table_DTR
Where Date = #Date and EmployeeID = #EmpID"
Dim cmd1 As SqlCommand = New SqlCommand(Query1, Connect)
cmd1.Parameters.Add("#Date", SqlDbType.DateTime).Value = dt
cmd1.Parameters.Add("#EmpID", SqlDbType.Int).Value = id
Using Reader As SqlDataReader = cmd1.ExecuteReader()
While Reader.Read()
MessageBox.Show(Reader("AfternoonTime-Out").ToString())
Loop
End Using
End Using
Note that I have changed the AddWithValue with a more precise Add specifying the parameter type. Otherwise, your code will be in the hand of whatever conversion rules the database engine decides to use to transform the string passed to AddWithValue to a DateTime.
It is quite common for this conversion to produce invalid values especially with dates

Error with searching between two dates on mschart

I have a problem with MSchart control. I have 2 fields on my database for date and time.
When I connect to my database and load X and Y values to my chart, there is no problem, but when i use search between 2 date in my query then mschart loads nothing. I'm using Text format for inDate1 and inTime1, here is my code:
Dim con As String = "Provider=Microsoft.ACE.OLEDB.12.0;Data Source=" + excel
Dim query As String = "SELECT inDate1,inTime1 FROM loginlog where personID=" + TextBox1.Text+" and inDate1 between "+ TextBox2.Text " and " + TextBox3.Text
Dim mycon As New OleDbConnection(con)
Dim command As New OleDbCommand(query, mycon)
mycon.Open()
chart1.DataSource = command.ExecuteReader()
chart1.Series(0).XValueMember = "inDate1"
chart1.Series(0).YValueType = ChartValueType.Time
chart1.Series(0).YValueMembers = "inTime1"
chart1.DataBind()
mycon.Close()
You really do not want to use text for dates. Instead, convert them to DateTimes (e.g. with DateTime.TryParse) and pass them as SQL parameters.The remark about passing as an SQL parameter applies to all parameters, including the personID.
So, your code could look something like:
Dim startDate As DateTime
Dim endDate As DateTime
If Not DateTime.TryParse(TextBox2.Text, startDate) Then
' there was an error parsing - do something useful
startDate = New DateTime(2000, 1, 1)
End If
If Not DateTime.TryParse(TextBox3.Text, endDate) Then
' there was an error parsing - do something useful
endDate = New DateTime(2100, 12, 31)
Else
' add a day to include it in the range selected in the SQL query
endDate = endDate.AddDays(1)
End If
Dim query As String = "SELECT inDate1, inTime1 FROM loginlog WHERE personID = #PersonID AND inDate1 BETWEEN #StartDate AND #EndDate"
Dim mycon As New OleDbConnection(con)
Dim command As New OleDbCommand(query, mycon)
command.Parameters.Add(New OleDbParameter With {.ParameterName = "#PersonID", .OleDbType = OleDbType.VarWChar, .Value = TextBox1.Text})
command.Parameters.Add(New OleDbParameter With {.ParameterName = "#StartDate", .OleDbType = OleDbType.Date, .Value = startDate})
command.Parameters.Add(New OleDbParameter With {.ParameterName = "#EndDate", .OleDbType = OleDbType.Date, .Value = endDate})
' now execute the query...