MS Access strings not matching in Query - ms-access

I have two externally linked tables in my Access DB. Table tblBatches contains, among others, two separate fields for PO and LineItem such as
Batch PO LI
1234567 4101234567 1
1234568 4101234567 4
1234569 4107654321 13
...
I have another table tblWIP that contains a field PO-LineItem such as:
PO-LI Date
4101234567-01 1/1/2016
4101234567-04 7/7/2016
4107654321-13 12/30/2016
...
All fields are stored as ShortText.
Since the tables are linked to external Excel files, I created a query qryBatchByPO-LI to process the PO and LI fields from tblBatches using the expression:
PO LI: [Purchasing Document]+"-"+Format([Purch# Doc: Item No#],"00")
I want to run a query that spits out Batch and Date as linked by the PO LI from my intermediate query, but it doesn't seem to be working properly.
Namely, it doesn't seem to be linking anytime the line item is less than 10 (therefore only one digit in the first table).
So, my query based on the above examples would only return:
Batch PO-LI Date
1234569 4107654321-13 12/30/2016
I've tried modifying my expression in a few ways, including:
PO LI: [Purchasing Document]+"-"+IIF(len([Purch# Doc: Item No#])<2,"0"+[Purch# Doc: Item No#],[Purch# Doc: Item No#])
I've even tried making a query to process the PO-LI field in the second table by splitting and rejoining the strings, to try and make sure everything is stored as strings, but no luck. In all situations, the results of my intermediate queries look correct, but any line items <10 are not appearing in my final queries.
I have no idea why these items aren't appearing, as again, to my eye the PO LI expression in qryBatchByPO-LI ends up looking the same and matching up with the PO-LI field in the tblWIP. Any help would be appreciated :/
I built the query using design view, but the SQL code ends up:
SELECT [qryBatchByPO-LI].Batch, [qryBatchByPO-LI].[PO LI],
tblBatches.[Short text], tblWIP.[Date]
FROM [qryBatchByPO-LI]
INNER JOIN tblEDSS_WIP ON [qryBatchByPO-LI].[PO LI] = tblEDSS_WIP.[PO-LI];

Build a query using this SQL;
SELECT tblBatches.BatchID, tblBatches.PO, tblBatches.LI, [PO] & '-' & IIf(Len([LI])<2,'0' & [LI],[LI]) AS PO-LI FROM tblBatches;
Then save this query as qdfOne. Then build another query and link to the table tblWIP like this;
INNER JOIN qdfOne ON tblWIP.PO-LI = qdfOne.PO-LI
When I do this I get all line items returned 1,4 & 13.
The difference is the use of the '&' to concatenate the strings. Using a '+' can end up treating the strings as numbers so that '01' (string) becomes '1' (number).

Related

MySQL question, How to loop through a list and return number of occurances for each in a table

I have a list of values.
'abc123', 'bdg432', 'eds321', 'hgd765', 'fds987', 'tdq343'
These values exist many times in a field in the "Items" table called "Itmcode".
I would like to execute the following query for each of the items codes from the list above.
SELECT
Items.Itmcode,
COUNT(*) AS `Total Items Sold`
FROM
Items
WHERE
Items.Itmcode = {Item Code From List} AND
Items.ItmStatus > 2
getting a result as follows.
Itmcode
Total Items Sold
abc123
4248
bdg432
98
eds321
78427
hgd765
151
tdq343
72164
I am pretty sure I need to use a loop to do this but i am not sure how.
I have never tried using loops before. I have looked at a commonly referenced example of a stored procedure that creates a list of numbers and outputs them into a string. For whatever reason I cant transfer that concept to reality. I am hoping that someone here can give help me to understand what I think is probably the simplest answer in the universe. I am just not getting it.

Comparing multiple fields in two datasets to return a 3rd value

I am in report builder and I have my primary dataset that is from a SQL database, I also then created a second dataset (enter data). I need to compare 2 fields from each dataset to retrieve the correct value from the 2nd dataset and populate a column on my report. I have tried the IIF statements and Lookup statements but I keep getting the error "report item expressions can only refer to fields within the current dataset".
I have a attached a screenshot of what I am trying to do....
The IIF statement I tried to use.. If Acctnum and prodid = each other return IncodeNumber
=IIF((Fields!AcctNum.Value=Fields!AcctNum.Value, "IncodeAccount") AND
(Fields!ProdId.Value =Fields!ProdId.Value, "IncodeAccount")),(Fields!IncodeNumber.Value, "IncodeAccount"),"True")
See code in my problem.
You need to use LOOKUP(). The problem with LOOKUP() is that is can only compare a single value from each dataset. However, we can easily get around this issue by concatenating the two values you need to compare.
Note: This assumes the expression will be in a tablix that is bound to your first dataset and that IncodeAccount is your second dataset - the values you want to lookup. If this is not the case just adjust the expression accordingly
So for you, you probably need to do something like this..
=LOOKUP(
Fields!AcctNum.Value & "||" & Fields!ProdId.Value,
Fields!AcctNum.Value & "||" & Fields!ProdId.Value,
Fields!IncodeNumber.Value,
"IncodeAccount"
)
I've used two pipe symbols to join the values to avoid incorrect matches being found. e.g. Account 123 and product ID 4567 would incorrectly match to Account 1234 and product ID 567 as they would both be 1234567 when joined. By using the || the match would be 123||4567 and 1234||567 respectively.
You may need to convert the values to string using CStr()
Alternative approach
If you are going to do this 'join' multiple times in the same dataset then you could add a calculated column to the dataset that concatenates the two columns. Then you can use this single field in the lookup which will make things a little simpler.
Or, you could do this concatenation in a database view which would make things even easier.

Testing if a row exists in a table for a report

I'm trying to write a report that lists all the rows from a master table and inserts a field ("Y"/"N") if the key exists in a current-use table. For example, the COLOR_MASTER table has 256 colors by COLOR_NAME (field/key). The CURRENT_PROJECTS has a row for each project and the COLOR_NAME (field). I want to list all the COLOR_MASTER rows and then on the same print line a "Y" or "N" if that COLOR_NAME is used in the CURRENT_PROJECTS table.
I've tried to mess around with it in the Design View and have had no luck. The JOIN that was created looks basically like this and how I want the report is following the dashes:
RIGHT JOIN COLOR_MASTER ON CURRENT_PROJECTS.COLOR_NAME =
COLOR_MASTER.COLOR_NAME ON CURRENT_PROJECTS.COLOR_NAME =
COLOR_MASTER.COLOR_NAME;
--------
Color Used
BLUE
RED Y
YELLOW
I have no expertise in JOINs and I don't understand why this JOIN was created or what I need to do to fix it. Based on my reading, I guess it's trying to do an outer join.
Currently, I'm just trying to show the COLOR_NAME if used as I don't know how to test that it is used and convert it to "Y". I don't care if the color is used once or twenty times and I don't really want any data from the CURRENT_PROJECTS table.
Under the "Used" column I now have "#Error" on all lines. So, I'm figuring that the RIGHT JOIN has an error.
Any guidance is appreciated.
Thanks
I expect the RIGHT JOIN is defined in the table Relationships builder and a query using the tables adopts the established link. If you want to change the join type in a query then with query in design view, double click on the line linking tables to open the Join Properties dialog.
If there is only one record per project in Current_Projects and a color can be used only once, simply:
SELECT Color_Master.Color_Name, IIf([Current_Projects].[Color_Name] Is Null,"N","Y") AS Used
FROM Color_Master LEFT JOIN Current_Projects ON Color_Master.Color_Name = Current_Projects.Color_Name;
However, it sounds like each color can be used for multiple projects. So will need to use GROUP BY or DISTINCT query joined to the Master_Colors table:
SELECT DISTINCT Current_Projects.Color_Name FROM Current_Projects;
SELECT Color_Master.Color_Name, IIf([Query1].[Color_Name] Is Null,"N","Y") AS Used
FROM Query1 RIGHT JOIN Color_Master ON Query1.Color_Name = Color_Master.Color_Name;
Here is all-in-one SQL:
SELECT Color_Master.Color_Name, IIf([Query1].[Color_Name] Is Null,"N","Y") AS Used
FROM (SELECT DISTINCT Current_Projects.Color_Name FROM Current_Projects) AS Query1
RIGHT JOIN Color_Master ON Query1.Color_Name = Color_Master.Color_Name;
If you don't want anything displayed for the N result then use Null without quote marks in the expression.
An alternative is DLookup() but domain aggregate functions can perform slowly in query or textbox expression.
Advise not to save the calculated value to table, just calculate when needed.
You don't have to do it all in one query. Start by building a query that as the IDs of all the colors currently in use. Name it something like ColorsInUse and save it.
It could be something as simple as:
SELECT [COLOR_NAME] FROM [CURRENT_PROJECTS] GROUP BY [COLOR_NAME]
Then all you have to do is run the following queries:
UPDATE [COLOR_MASTER] SET [MyField]="N"
UPDATE [COLOR_MASTER] SET [MyField]="Y" WHERE [COLOR_NAME] IN [ColorsInUse]
Another way of doing it is by using DLookup. Something like this:
UPDATE [COLOR_MASTER] SET [MyField]=IIF(NZ(DLookup("[COLOR_NAME]","[CURRENT_PROJECTS]","[COLOR_NAME]='" & [COLOR_NAME] & "'"),"")="","N","Y")
Some notes: You should not use a text field (like a name) as your key. You should always use numerical IDs. You should also never use a text Y/N. Use an actual Yes/No field instead.

MS Access Query using IFF to compare values

I am trying to build a query which will look at the data in two fields in two different tables and check to see if the data is the same, if it is I want it to return the number of times it is matched, if it isn't I simply want it to return the text saying "No viewings".
I have constructed this query in my access database which has the field from the first table "Property" and the second field I want it to compare the data with, "Viewings". I have build the following expression using the build tool, however I am stuck to make it work since every time I get this error message when trying to run the query: "Your query does not include the specified expression 'Property Viewed' as part of an aggregate function."
totalViewings: IIf([Viewings]![Property Viewed]=[Property]![ID],Count([Viewings]![Property Viewed]=[Property]![ID]),"No Viewings")
Any help how to overcome this error would be very appreciated.
Thanks
I would suggest doing something like this:
1) Assuming this is something you are developing yourself, make sure your data structure is all in order first. Since I dislike relatively code-hostile identifiers, I'd have the tables as so -
Properties - PropertyID (AutoNumber, primary key), HouseNumberOrName, Street, etc.
Viewings - ViewingID (AutoNumber, primary key), PropertyID (Number/Long Integer), ViewingDate, etc.
In the Relationships view, Properties.PropertyID would then be set up to point to Viewings.PropertyID in a one-to-many relation.
2) Your actual query I would then break into two, the first to compile the data and the second to format it for display. The first would go like this, saved as ViewingCounts...
SELECT Properties.PropertyID, Count(Viewings.PropertyID) As ViewingCount
FROM Properties LEFT JOIN Viewings ON Properties.PropertyID = Viewings.PropertyID
GROUP BY Properties.PropertyID;
... and the second like this, saved as ViewingCountsForDisplay:
SELECT Properties.*, IIf(ViewingCount = 0, 'No viewings', ViewingCount) AS Viewings
FROM Properties INNER JOIN ViewingCounts ON Properties.PropertyID = ViewingCounts.PropertyID
ORDER BY Properties.PropertyID;

concatenate using Allen Browne's example

I am using the 'concatenate related' module created by Allen Browne to concatenate rows into a single field. At first I had a lookup field at the table level and later realized this is not a good approach. So I deleted the lookup column and instead made a query for selecting values from the lookup table on my form and then store that value as a number in the table.
The module works when I concatenate the values but it is listing the number (id) whereas I would like the actual description (i.e. 1 = Red, 2 = Blue, etc.)
My SQL query code is as follows:
SELECT DISTINCT
tblCompany.JobID,
concatrelated("type","tblMonitor","JobID = " & [jobID]) AS Expr1
FROM tblCompany;
I would like "type" to display the description instead of the number. I know if I store my lookup value as text instead of number it will work. But for efficiency it seems the number should be stored in the table and then query for the description when you need it....or maybe text is fine??? I'm guessing I would need to add the lookup table to this query. I have tried but with no luck so far.
Create a query which joins tblMonitor with the table which holds the type description field. Then use that query with ConcatRelated.
ConcatRelated("type_descriptn","YourQuery","JobID = " & [jobID])