Can I add an object to a struct in VB.net? - vb.net

I have a data struct for a piece of lumber. I've built a class to handle dimensions (architectural, metric, etc... ) that I'd like to make the data type of the length member of this struct. VB says I can't use 'new' in my definition unless I make the member 'Shared'. If I make the member 'Shared' I can't see the data when I try to access the member in my code.
Public Structure PieceInfo
Dim ProjectNumber As String
Dim ProjectName As String
Dim BuildingType As String
Dim BuildingNumber As String
Dim BLevel As String
Dim Batch As String
Dim Trussname As String
Dim Span As Single
Dim PieceName As String
Dim LumberType As String
Shared PieceLength As New clsDimension
Shared StockLength As New clsDimension
Dim LeftSplicePlate As String
Dim RightSplicePlate As String
End Structure
How can I use my "clsDimension" object as the data type for the "Length" members of my struct?

As all the comments indicate: You should change your Struct to a class because you want to reference it. And due to Structs being value types and Classes being reference types, This is what you want:
Public Class PieceInfo
Dim ProjectNumber As String
Dim ProjectName As String
Dim BuildingType As String
Dim BuildingNumber As String
Dim BLevel As String
Dim Batch As String
Dim Trussname As String
Dim Span As Single
Dim PieceName As String
Dim LumberType As String
Shared PieceLength As New clsDimension
Shared StockLength As New clsDimension
Dim LeftSplicePlate As String
Dim RightSplicePlate As String
End Class

.NET Structure don't have default constructor, you'll have to create your own (or a function to initialize the values). But that kind of defeat the purpose of the struct.
Public Structure PieceInfo
Dim ProjectNumber As String
Dim ProjectName As String
Dim BuildingType As String
Dim BuildingNumber As String
Dim BLevel As String
Dim Batch As String
Dim Trussname As String
Dim Span As Single
Dim PieceName As String
Dim LumberType As String
Dim PieceLength As clsDimension
Dim StockLength As clsDimension
Dim LeftSplicePlate As String
Dim RightSplicePlate As String
Public Sub New(ByVal t As String)
PieceLength = New clsDimension
StockLength = New clsDimension
End Sub
End Structure
But like others said, changing it to a class is the right thing to do. Class is reference type and structure is value type.

Related

Class not registered error after migration

Issue with custom VB.net solution after moving user to new Windows 10.
Removing, re-adding various references. Cleaning and Rebuilding.
Public Class mainForm
Dim exc As Excel.Application
Dim wd As Word.Application
Private wsClient As New WebClient()
Dim customAccForm As New customAccessories
Dim custNumArray(4200) As String
Dim preload As Boolean = False
Public custName As String = ""
Public custPhone As String = ""
Public custAddy, custSuite, custCity As String
Dim accessoriesprice, accessoriesWeight As Double
Dim chkQty(20), chkPrc(20), chkWt(20) As Double
Dim chkCtr As Integer = 0
Dim chkDsc(20) As String
Dim currName As String
Dim updateQuotes As Boolean
Dim thr, thr2 As Threading.Thread
Dim bodyTxt, quotedFreight As String
Public USPS_UserID As String = "USERNAME"
I've moved a user from an older Windows 7 machine to a new windows 10 machine. I have a custom built VB.net application that will not compile on the new machine. I get a "class not registered" message and the debugger highlights a variable declaration at the top of Forms class. What's weird is it is on a declaration for a String, the USPS_UserID declaration in the code above. Even weirder is that I can reorder my declarations and it will show the registration error for another class (String, Integer, Double). It varies.

VB.NET, keywords as variable names

I have to deserialize some json data string into structure.
Problem is that data names conflicts vith VB keywords what is in C# not a case.
This is json string:
{"id":2526068,"date":"2019-07-21T19:15:17.4468196+02:00","error":""}
Problematic names are obviously "date" and "error". Somewhere I found that such variables should be surrended with []. But this don't work for me.
Here is my code:
Structure reqjson
Dim id As String
Dim [date] As String
Dim [error] As String
End Structure
Dim idnum As Long = 0
Dim sldate As String = ""
If Not String.IsNullOrEmpty(jsonstr) Then
Dim r As reqjson = JsonConvert.DeserializeObject(Of reqjson)(jsonstr)
idnum = CLng(r.id)
sladate = r.date.ToString("dd.MM.yyyy. hh:mm:ss.fff")
End If
Problem is that deserializer can't deserialize data if they don't have a same name what VB don't allow. In C# this declaration is legal:
struct reqjson{
string id;
string date;
string error;
};
But not in VB.NET. What to do here?
I don't see any problem with your deserialization. Your code works for me!
But perhaps you should address a couple potential issues. Don't use Dim for class level fields. Use Public or Private
Structure reqjson
Public id As String
Public [date] As String
Public [error] As String
End Structure
And I'm not changing anything here, other than adding the json string myself
Public Shared Sub foo()
Dim jsonstr = "{""id"":2526068,""Date"":""2019-07-21T19:15:17.4468196+02:00"",""error"":""""}"
Dim idnum As Long = 0
Dim sldate As String = ""
If Not String.IsNullOrEmpty(jsonstr) Then
Dim r As reqjson = JsonConvert.DeserializeObject(Of reqjson)(jsonstr)
idnum = CLng(r.id)
However, you are doing String.ToString(). Try this instead
sldate = Date.Parse(r.date).ToString("dd.MM.yyyy. hh:mm:ss.fff")
End If
End Sub
Or better yet, use an actual date in the struct
Structure reqjson
Public id As String
Public [date] As Date
Public [error] As String
End Structure
which makes your original code work
sldate = r.date.ToString("dd.MM.yyyy. hh:mm:ss.fff")

vb.net - How to concatenate a variable(trimmed) to another variable to complete its variable name

Needed code is something like this:
Dim myArray(0) As String
Dim ay As String = "ay"
myArr & ay(0) = "asd"
I've tried but did not worked
Dim classlist1(0) As String
Dim classlist2(0) As String
Dim classlist3(0) As String
Dim classlist4(0) As String
Dim count As Integer = 0
For _year As Integer = 1 To 4
("classlist" & _year)(count) = "hi"
count += 1
Next
Any time you see something like this:
Dim classlist1(0) As String
Dim classlist2(0) As String
Dim classlist3(0) As String
' etc.
It's an indication that you're using the wrong data structure. Instead of trying to dynamically build variable names (which isn't really possible in a static language, at least not without some really ugly reflection code with a high potential for runtime errors), just use a collection.
For example, if you want a collection of strings:
Dim classList As New List(Of String)()
And if you want a collection of collections of strings:
Dim classLists As New List(Of List(Of String))()
Then you can reference the nested lists within the parent list. So to add your first "year" of classes:
classLists.Add(new List(Of String))
And add a class to that year:
classLists(0).Add("some value")
As you can see, it starts to get a little difficult to keep track of the data structures. This is where creating custom types and structures becomes very useful. For example, rather than representing a "year" as a list of strings, create an actual Year class. That class can internally hold a list of strings, and other logic/data.
Try Dictionary<TKey, TValue> Class From MSDN.
Dim classLists As New Dictionary(Of String, String)()
'Add items with keys
For _year As Integer = 1 To 4
classLists.Add(String.Format("classlist{0}",_year), "hi")
Next
And you can get value by key later
Dim key As String = "classlist2"
Dim value As String = classLists(key)

How do we create array of string arrays in vba?

Dim a(10) as string
Dim b(10) as string
Dim c(10) as string
Dim d(10) as String
d= Array(a,b,c)
This isn't working.
You were very close in your example. All you need to do is to declare "d" as Variant and not as String-array, because it isnt:
Private Sub arraytest()
Dim a(10) As String
Dim b(10) As String
Dim c(10) As String
a(0) = "test"
Dim arrD As Variant 'Dimensionless variable to hold the result of "Array-Function"
arrD = Array(a, b, c)
Debug.Print arrD(0)(0)
End Sub
Think of "Array" as a function building an Array-Object with all the correct dimensions and properties. All you need is something to hold that (a Variant), whatever it really becomes.
Note that contrary to normal multi-dimensional arrays, you access the values via (x)(y) and not (x,y).

VB.net Iterating Structures and setting data types

I am using the following structure many times throughout my code to pass a set of data to a function:
Public Structure MyStruct
Dim ResourceID As String
Dim RSRCName As String
Dim CommercialType As String
Dim ParticipantName As String
Dim ASReserveZone As String
Dim SCADAStatusQuality As String
Dim SCADAStatus As String
Dim SCADAMWQuality As String
Dim ManualDispatchReason As String
Dim RegUpQual As Boolean
Dim RegDownQual As Boolean
Dim SuppQual As Boolean
Dim SpinQual As Boolean
Dim UseEmergencyLimits As Boolean
Dim FollowLastDispatch As Boolean
Dim ASOfferCurveDict As HybridDictionary
Dim XIC As Integer
Dim PriceBased As Integer
Dim PNodeID As Integer
Dim Committed As Integer
Dim CommitmentStatus As Integer
Dim ManualDispatch As Integer
Dim LastApprdNumOfIntervalsToMax As Integer
Dim MWCurve() As Double
Dim EnergyOfferCurve() As Double
Dim PlannedMW As Double
Dim SCADAMW As Double
Dim InitialOnHours As Double
Dim LastApprdDispatchMW As Double
Dim TotalRampedCRDeployMW As Double
End Structure
Dim Struct as MyStruct
I can use Struct = Nothing to reset the data, but I would rather iterate through the structure and set all the numeric values to 999999999. Any idea how to do this?
You could do it with reflection, but I wouldn't necessarily recommend it. I'd sooner just add a Clear or Reset method to the structure which sets all the values to their default values. Another option would be to set the default values when the fields are declared:
Public Structure MyStruct
' ...
Dim XIC As Integer = 999999999
Dim PriceBased As Integer = 999999999
Dim PNodeID As Integer = 999999999
' ...
End Structure
Then, to reset a variable to all the default values, just do this:
myVariable = New MyStruct()
I should also mention, unless it really needs to be a structure for some reason, you should change this to a class. It's quite a lot of data to be passing around on the stack all the time.