MS Access using variables to unpivot 100+ columns - ms-access

I have a pivot table that looks like this (the table layout cannot be changed) with 200 columns to be unpivoted (the fieldnames are indeed numbers)
Template | Row | 1 | 2 | 3 | 4 | ...| 200
abc | 1 | 5 | 4 | | | |
abc | 2 | | 45| | | |
abc | 3 | | 35| | | |
The table should look like this:
Template | row | column | value |
abc | 1 | 1 | 5 |
abc | 1 | 2 | 4 |
abc | 2 | 1 | |
abc | 2 | 2 | 45 |
with 200 columns to be unpivoted, I can't fathom creating a SQL statement with 200 UNION ALLs, so I figured I will loop an insert into by using a variable.
The difficulty I am having is that I don't know how to use the variable both as a value as well as a fieldname.
In Pseudo-SQL my query would look like this:
Insert Into TheDestination (Template, Row, Column, Value) Select Template,
Row, $x as column, TheTable.$x from TheTable
where X would increase by 1 for each iteration.
This is what I came up with, but I am getting a syntax error. What is the correct statement? Do I need to use a 2nd variable?
Private Sub Unpivot_Click()
Dim x As Integer
Dim columncount As Integer
Dim setRST As DAO.Recordset
Dim sqlstr As String
Set setRST = CurrentDb.OpenRecordset("Select * from TheTable")
columncount = setRST.Fields.Count
While Not setRST.EOF
For x = 1 To columncount
CurrentDb.Execute "Insert Into TheDestination VALUES (Template, Rownumber,
Columnnumber, Result) Select Template, row, "&x&" as column, "&x&" from
TheTable"
Next x
Wend
End Sub
Thank you in advance!

Your INSERT INTO statement looks really weird, and it appears like you're not assigning the right values.
Using a querydef and parameters avoids problems with string concatenation, and minimizes some assignments.
Try the following:
Private Sub Unpivot_Click()
Dim x As Integer
Dim columncount As Integer
Dim setRST As DAO.Recordset
Dim sqlstr As String
Dim qdf As DAO.QueryDef
Dim fld As DAO.Field
Set setRST = CurrentDb.OpenRecordset("Select * from TheTable")
columncount = setRST.Fields.Count
Set qdf = db.CreateQueryDef ("", "Insert Into TheDestination ([Template], [Row],
[Column], [Result]) VALUES (#Template, #RowNumber, #ColumnNumber, #Result)")
Do While Not setRST.EOF
qdf.Parameters("#Template") = setRST!Template
qdf.Parameters("#RowNumber") = setRST!row
For Each fld In setRST.Fields
If IsNumeric(fld.Name) Then
qdf.Parameters("#ColumnNumber") = fld.Name
qdf.Parameters("#Result") = fld.Value
qdf.Execute
End If
Next fld
setRST.MoveNext
Loop
End Sub

Related

hyperlink based on fields value in Microsoft access table

how to use hyperlink to open files based on fields value?
for example:
The file name is word 289.docx and located inside of z:/data/
this is Microsoft access table:
Field1
Filed2
hyperlink
word
289
="z:/data/"&[Field1] &" "& [Filed2] & ".docx"
When I clicked on hyperlink get an error below:
Microsoft access can't follow the hyperlink
I try to use another way like below:
link#"z:/data/" & [Field1] &" "& [Filed2] & ".docx"#
but doesn't work again.
why does this hyperlink not work?
Here is my solution based on June7's comments. I found this link helpful: https://www.devhut.net/microsoft-access-hyperlinks/
I couldn't find a way to reference functions inside the hyperlink, but I could write a vba routine to automate updating the hyperlink in the table from the fields
Public Sub updateHyperlinks()
Dim rs As Recordset
Dim db As Database
Set db = CurrentDb
Set rs = db.OpenRecordset("Mytablename")
Do While Not rs.EOF
rs.Edit
rs!Hyperlink = "myvisiblelinktext#" & rs!Field1 & rs!Field2
rs.Update
rs.MoveNext
Loop
rs.Close
db.Close
Set rs = Nothing
Set db = Nothing
End Sub
One caveat Field1 includes the file extension for more generality
edit:
---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
| ID | hyperlink | filename | filelocation | hyperlinkaddress |
---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
| 2 | | board.xlsx | C:\Users\bubblegum\Desktop\ | |
---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
| 3 | | app.docx | C:\Users\bubblegum\Desktop\ | |
---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
table after updating hyperlinks with address inside hyperlink manually added. the table itself shows the hyperlink in the hyperlink column.
---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
| ID | hyperlink | filename | filelocation | hyperlinkaddress |
---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
| 2 | myvisiblelinktext#C:\Use | board.xlsx | C:\Users\bubblegum\Desktop\ | C:\Users\bubblegum\Desktop\board.xlsx |
---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
| 3 | myvisiblelinktext#C:\Use | app.docx | C:\Users\bubblegum\Desktop\ | C:\Users\bubblegum\Desktop\app.docx |
---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

Access Merge Text from Different Rows

I have a Access DB with following scheme:
+---------+---------+-----------+------------+-------------------------------------------+
| BrandNr | TextNr | LangCode | OngoingNr | Text |
+---------+---------+-----------+------------+-------------------------------------------+
| 1 | AB | 1 | 1 | Text beginns here but it doesn't end here |
| 1 | AB | 1 | 2 | Text isn't finished so need second row |
| 1 | AC | 2 | 1 | New text |
| 2 | hg2 | 1 | 1 | New brand new text |
+---------+---------+-----------+------------+-------------------------------------------+
Now I need to merge the text where BrandNR, TextNr and LangCode are the same. The Text should be ordered by the OngoingNr.
Some ideas?
I believe this will require VBA.
One possible method is to call a VBA function which defines a Static string-type variable that is initialised to an empty string for every new combination of BrandNR, TextNr and LangCode, else concatenated with itself.
Open the VBA IDE using Alt+F11
Insert a new Public Module Alt+I,M
Copy the following basic code into the new Module:
Function Concat(strInp As String, lngOrd As Long) As String
Static strTmp As String
If lngOrd = 1 Then strTmp = strInp Else strTmp = strTmp & " " & strInp
Concat = strTmp
End Function
In MS Access, create a new query with the following SQL, changing MyTable to the name of your table:
select q.BrandNr, q.TextNr, q.LangCode, Concat(q.Text,q.OngoingNr) as Merged
from
(
select t.* from MyTable t
order by t.BrandNr, t.TextNr, t.LangCode, t.OngoingNr
) q

Get a list of column names only

I've been looking around the Internet for quite some time now, but I can't find a way to get a list of just column names. I don't care about the data each column has.
I want to take that list and compare it against a collection. I'm using the VB.NET MySqlConnector. I'm new to using the connector.
Edit:
Dim mscCMD As MySqlCommand = New MySqlCommand("SHOW COLUMNS FROM OCN.cpu", msc)
Dim sqlReader As MySqlDataReader = mscCMD.ExecuteReader()
Dim b As Integer = 0
Dim c As Integer = 0
While sqlReader.Read
msProjects(c) = sqlReader.**Item**(b)
b += 1
c += 1
End While
Never mind, I figured it out. I had to choose Item, not getName.
Edit: Perhaps I didn't just yet. It's reading one row. I'm unsure how to move to the next row. For example
mysql> SHOW COLUMNS FROM City;
+------------+----------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+------------+----------+------+-----+---------+----------------+
**Id | int(11) | NO | PRI | NULL | auto_increment**
| Name | char(35) | NO | | | |
| Country | char(3) | NO | UNI | | |
| District | char(20) | YES | MUL | | |
| Population | int(11) | NO | | 0 | |
+------------+----------+------+-----+---------+----------------+
5 rows in set (0.00 sec)
That's the row it reads it reads. Once you go past the 5th item, you're out of bounds.
You can use the metadata from a result set:
final ResultSet rs = statement.executeQuery("SELECT * FROM `" + tableName +"` LIMIT 0,1;");
final ResultSetMetaData metaData = rs.getMetaData();
for(int i=1; i<metaData.getColumnCount(); i++)
{
System.out.println("" + metaData.getColumnName(i));
}
Also, you can get the java.sql.Types column type the same way.
Got it. Found the answer from a MS KB article.
https://support.microsoft.com/en-us/kb/310108
For Each myField In schemaTable.Rows
'For each property of the field...
For Each myProperty In schemaTable.Columns
'Display the field name and value.
Console.WriteLine(myProperty.ColumnName & " = " & myField(myProperty).ToString())
Next
Console.WriteLine()
'Pause.
Console.ReadLine()
Next
Specifically myField(myProperty).ToStringwill get you the column names. It will also contain other things about the column. You will have to sort through it, but all the column names from your table will be in there.

Why does MySQL query read integer column as byte array in VB.net?

I've got a simple MySQL table, which contains an "Age" column with integer and null values.
Customers
+--------------+--------------+ .... +------------+
| Name | Location | | Age |
+--------------+--------------+ .... +------------+
| Murphy | US | | 23 |
| Pierre | France | | 42 |
| Rafael | Spain | | null |
| Paulo | Italy | | 21 |
+--------------+--------------+ .... +------------+
Name and Location are type varChar and Age is type int.
However when I attempt to read from it in my VB.net code...
Dim connStr as string = Session("connectionString") 'My Connection String'
Dim sql As String = "SELECT * FROM Customers;"
Dim conn As MySqlConnection = New MySqlConnection(connStr)
conn.Open()
Dim da As MySqlDataAdapter = New MySqlDataAdapter(sql , conn)
Dim ds as new dataset
da.Fill(ds)
... the Age column in the dataset ds has System.Byte[] in every cell instead of the integer value.
Why is this happening?
Try to make sure that Age column only returns integer values.
Change your select to
SELECT Name,Location,IFNULL(Age,0) AS Age FROM Customers;
Another check, does your dataset allow dbnull? There is a property you can change. Maybe give that a try also with your inital SELECT * FROM Customers;

Formatting tables imported via a report

I have a few reports that I get every day that have to be imported into a database, MS Access, in a particular way. The problem is, the way the reports are laid out makes it difficult to do so.
Program: Name A
Date | Description | Other | Stuff
Date | Description | Other | Stuff
Program: Name B
Date | Description | Other | Stuff
Date | Description | Other | Stuff
Program: Name C
Date | Description | Other | Stuff
Date | Description | Other | Stuff
Basically, what I would like it to do is look like this.
Program: Name A | Date | Description | Other | Stuff
Program: Name A | Date | Description | Other | Stuff
Program: Name B | Date | Description | Other | Stuff
Program: Name B | Date | Description | Other | Stuff
Program: Name C | Date | Description | Other | Stuff
Program: Name C | Date | Description | Other | Stuff
I've played around with a couple different solutions, but so far nothing has done the job.
Thanks for any help!
Something like:
Dim xl As New Excel.Application
Dim ws As Excel.Worksheet
Dim rng As Excel.Range
Dim rs As DAO.Recordset
Dim db As Database
Set db = CurrentDb
''Run once
''s = "create table reporttable (id counter primary key, program text, " _
'' & "pdate text, [description] text, other text, stuff text)"
''db.Execute s, dbFailOnError
Set rs = db.OpenRecordset("ReportTable")
xl.Visible = True ''dev
Set ws = xl.Workbooks.Open("z:\docs\report.xlsx").Sheets("Sheet1")
Set rng = ws.UsedRange
For i = 1 To rng.Rows.Count
If rng.Cells(i, 1) Like "Program*" Then
progdat = rng.Cells(i, 1)
Else
rs.AddNew
rs!program = progdat
rs!pdate = rng.Cells(i, 1) ''Text, because you cannot trust reports
rs!Description = rng.Cells(i, 2)
rs!Other = rng.Cells(i, 3)
rs!Stuff = rng.Cells(i, 4)
rs.Update
End If
Next
Set rs = Nothing
Set rng = Nothing
ws.Parent.Close
Set ws = Nothing
xl.Quit
Set xl = Nothing