Issue in running an update query in access - sql

I have a relational access database and I want to update a table based on another table. You can see relations in the picture. SQL statement is as bellow. When I try to update I face "Your query does not include the specified expression "TRX900" as part of an aggregate function."
But When I try to see in datasheet view mode, it is OK. Your support is appreciated.
Update
(
(
Sites INNER JOIN Cells ON Sites.ID = Cells.SiteID
) INNER JOIN Cells_2G ON Cells.ID = Cells_2G.[Cell ID]
) ,
ImportedTRX INNER JOIN ActiveStatus ON ImportedTRX.[Active Status] = ActiveStatus.Status
Set
Cells_2G.TRX900=Sum( IIF ( ImportedTRX.Frequency <=124 , 1,0 ) )
,
Cells_2G.TRX1800=Sum( IIF ( ImportedTRX.Frequency >=512 , 1,0 ) )
WHERE
(
ImportedTRX.[cell name]=[Sites].[SiteID] & [Cells].[Cell_Order]
AND
ActiveStatus.YesNo=True
)
;
Sites table sample:
-----------------------
| ID | SiteID |
-----------------------
| 1 | T4000X |
-----------------------
Cells table sample:
------------------------------------
| ID | SiteID | Cell_Order |
------------------------------------
| 1 | 1 | A |
| 2 | 1 | B |
| 3 | 1 | C |
------------------------------------
Cell_2G sample table:
------------------------------------------------------------
| ID | CellID | Expected TRX900 | Expected TRX1800 |
------------------------------------------------------------
| 1 | 1 | 1 | 2 |
| 2 | 2 | 2 | 1 |
| 3 | 3 | 2 | 3 |
------------------------------------------------------------
ImportedTRX table sample
-------------------------
| Cell Name | Frequency |
-------------------------
| T4000XA | 800 |
| T4000XA | 801 |
| T4000XA | 22 |
| T4000XB | 4 |
| T4000XB | 33 |
| T4000XB | 860 |
| T4000XC | 20 |
| T4000XC | 21 |
| T4000XC | 840 |
| T4000XC | 841 |
| T4000XC | 842 |
-------------------------

There are two approaches to this problem:
Create 2 queries, 1 preparing the result and 1 executing the update, where the
Parse using VBA.
I'm going to share the second approach.
The first query is essentially your current query converted to a SELECT query, only the table you're updating has been removed
Query Query1:
SELECT
Sum( IIF ( ImportedTRX.Frequency <=124 , 1,0 ) ) As TRX900
,
Sum( IIF ( ImportedTRX.Frequency >=512 , 1,0 ) ) As TRX1800,
Cells.ID
FROM
(
Sites INNER JOIN Cells ON Sites.ID = Cells.SiteID
),
ImportedTRX INNER JOIN ActiveStatus ON ImportedTRX.[Active Status] = ActiveStatus.Status
WHERE
(
ImportedTRX.[cell name]=[Sites].[SiteID] & [Cells].[Cell_Order]
AND
ActiveStatus.YesNo=True
)
GROUP BY
Cells.ID
;
Then, we're going to update the table using DLookUp and querying from that query:
Query Query2:
UPDATE Cells_2G
SET
Cells_2G.TRX900= DLookUp("TRX900", "Query1", "ID = " & [Cell ID]),
Cells_2G.TRX1800= DLookUp("TRX1800", "Query1", "ID = " & [Cell ID])
This produces the desired result, though you haven't included the ActiveStatus table so I couldn't include that in testing.
Unfortunately, the statement is too complex for me to write into a single update query, so this two-step approach is the best non-VBA solution I can come up with.

After some try I used following code, but it is slow yet.
UPDATE
ImportedTRX,
(
Sites INNER JOIN Cells ON Sites.ID=Cells.SiteID
) INNER JOIN Cells_2G ON Cells.ID= cells_2G.[Cell ID]
SET
Cells_2G.TRX900 = DSUM("IIF(Frequency<=124,1,0)", "ImportedTRX", "[Cell Name]='"& Sites.SiteID & Cells.Cell_Order & "'")
,
Cells_2G.TRX1800 = DSUM("IIF(Frequency>=512,1,0)", "ImportedTRX", "[Cell Name]='"& Sites.SiteID & Cells.Cell_Order & "'")
WHERE
(
ImportedTRX.[Cell Name]=Sites.[SiteID] & Cells.[Cell_Order]
);

Related

Implementing where condition in DAX

I have a scenario wherein I want to implement a BELOW SQL Query in Dax:
select count(distinct a.ID)
from Table1 a
join Table2 b
on a.ID=b.ID
where a.[In_Time] = "No" OR b.[In Time] = "No"
how do I implement using Dax?
You did not provide much of details as to what is is the relationship between t1 and t2 and whether you expect this through a DAX query or DAX measure.
Assuming you want this to be returned through DAX query with no relationship between t1 and t2 an equivalent DAX query would be following. It joins a filtered t1 and filtered t2 on desired criteria.
t1
| id | inTime |
|----|--------|
| 1 | yes |
| 1 | no |
| 2 | no |
| 3 | no |
| 4 | no |
| 5 | no |
| 6 | no |
t2
| id | inTime |
|----|--------|
| 1 | yes |
| 1 | no |
| 2 | yes |
| 3 | no |
| 5 | no |
Query
Table =
VAR _1 =
DISTINCT (
NATURALINNERJOIN (
SELECTCOLUMNS (
FILTER ( t1, t1[inTime] = "no" ),
"id", t1[id] + 0,
"inTIme", t1[inTime] & ""
),
SELECTCOLUMNS (
FILTER ( t2, t2[inTim] = "no" ),
"id", t2[id] + 0,
"inTIme", t2[inTim] & ""
)
)
)
VAR _2 =
ROW ( "count", COUNTX ( _1, [id] ) )
RETURN
_2
returns the following for VAR _1
| id | inTime |
|----|--------|
| 1 | no |
| 3 | no |
| 5 | no |

Joining table on two columns only joins it on a single

How do I correctly join a table on two columns. My issue is that the result is not correct as it only joins on a single column.
This question started of in this other question: SQL query returns product of results instead of sum . I am creating a new question as there is an other issue I am trying to solve.
I join a table of materials on a table which contains multiple supply and disposal movements. Each movement references a material id. I would like to join the material on each movement.
My query:
SELECT supply_material_refer, disposal_material_refer, material_id, material_name
FROM "construction_sites"
JOIN projects ON construction_sites.project_refer = projects.project_id
JOIN addresses ON construction_sites.address_refer = addresses.address_id
cross join lateral ( select *
from (select row_number() over () as rn, *
from supplies
where supplies.supply_project_refer = projects.project_id) as supplies
full join (select row_number() over () as rn, *
from disposals
where disposals.disposal_project_refer = projects.project_id
) as disposals
on (supplies.rn = disposals.rn)
) as combined
LEFT JOIN materials material ON combined.disposal_material_refer = material.material_id
OR combined.supply_material_refer = material.material_id
WHERE (projects.project_name = 'Project 15')
ORDER BY construction_site_id asc;
The result of the query:
+-----------------------+-------------------------+-------------+---------------+
| supply_material_refer | disposal_material_refer | material_id | material_name |
+-----------------------+-------------------------+-------------+---------------+
| 1 | 1 | 1 | Materialtest |
| 2 | 1 | 1 | Materialtest |
| 2 | 1 | 2 | Dirt |
| 1 | 1 | 1 | Materialtest |
| 2 | 1 | 1 | Materialtest |
| 2 | 1 | 2 | Dirt |
| 1 | (null) | 1 | Materialtest |
| 4 | (null) | 4 | Stones |
+-----------------------+-------------------------+-------------+---------------+
An example line I have issues with:
+------------------------+-------------------------+-------------+---------------+
| supply_material_refer | disposal_material_refer | material_id | material_name |
+------------------------+-------------------------+-------------+---------------+
| 2 | 1 | 1 | Materialtest |
+------------------------+-------------------------+-------------+---------------+
A prefered output would be like:
+------------------------+----------------------+-------------------------+------------------------+
| supply_material_refer | supply_material_name | disposal_material_refer | disposal_material_name |
+------------------------+----------------------+-------------------------+------------------------+
| 2 | Dirt | 1 | Materialtest |
+------------------------+----------------------+-------------------------+------------------------+
I have created a sqlfiddle with dummy data: http://www.sqlfiddle.com/#!17/863d78/2
To my understanding the solution would be to have a disposal_material column and and supply_material column for the material names. I do not know how I can achieve this goal though...
Thanks for any help!

How can I subtract two row's values within same column using sql query in access?

(query access)
This is the table structure:
+-----+--------+--------+
| id | name | sub1 |
+-----+--------+--------+
| 1 | ABC | 6.27% |
| 2 | ABC | 7.47% |
| 3 | PQR | 3.39% |
| 4 | PQR | 2.21% |
+-----+--------+--------+
I want to subtract Sub1
Output should be:
+-----+--------+---------+------------------------------------+
| id | name | sub1 | |
+-----+--------+---------+------------------------------------+
| 1 | ABC | 6.27% | 0 First Rec no need Subtract |
| 2 | ABC | 7.47% | 1.2% <=(7.47-6.27) |
| 3 | PQR | 3.39% | 0 First Rec no need Subtract |
| 4 | PQR | 2.21% | -1.18% <=(2.21-3.39) |
+-----+--------+---------+------------------------------------+
Thank you so much.
If you can guarantee consecutive id values, then the following presents an alternative:
select t.*, nz(t.sub1-u.sub1,0) as sub2
from YourTable t left join YourTable u on t.name = u.name and t.id = u.id+1
Change YourTable to the name of your table.
This is painful, but you can do:
select t.*,
(select top 1 t2.sub1
from t as t2
where t2.name = t.name and t2.id < t.id
order by t2.id desc
) as prev_sub1
from t;
This gives the previous value or NULL for the first row. You can just use - for the subtraction.
An index on (name, id) would help a bit with performance. However, if you can upgrade to a better database, you can then just use lag().

Can't show all records with the same id while join in oracle xe 11g

I'm getting this message while using this query, is there anything wrong?
SELECT t.tanggal_transaksi, o.nama_lengkap, SUM(td.harga * td.qty) total
FROM transaksi t, transaksi_detail td, operator o
WHERE td.transaksi_id = t.transaksi_id AND o.operator_id = t.operator_id
GROUP BY t.transaksi_id
Updated :
After using the answer from #Barbaros Özhan using this query :
SELECT t.tanggal_transaksi, o.nama_lengkap, SUM(td.harga * td.qty) total
FROM transaksi t
INNER JOIN transaksi_detail td ON ( td.transaksi_id = t.transaksi_id )
INNER JOIN operator o ON ( o.operator_id = t.operator_id )
GROUP BY t.tanggal_transaksi, o.nama_lengkap;
the data is successfully displayed. but, there are few problems that occur, the value of the same operator_id cannot appear more than 1 time. Here is the sample data :
+--------------+-------------+-------------------+
| TRANSAKSI_ID | OPERATOR_ID | TANGGAL_TRANSAKSI |
+--------------+-------------+-------------------+
| 1 | 5 | 09/29/2018 |
| 2 | 3 | 09/29/2018 |
| 3 | 3 | 09/29/2018 |
| 4 | 1 | 09/29/2018 |
| 5 | 1 | 09/29/2018 |
+--------------+-------------+-------------------+
After use the query command, the output is :
+-------------------+------------------+--------+
| TANGGAL_TRANSAKSI | NAMA_LENGKAP | TOTAL |
+-------------------+------------------+--------+
| 09/29/2018 | Lina Harun | 419800 |
| 09/29/2018 | Titro Kusumo | 484000 |
| 09/29/2018 | Muhammad Kusnadi | 402000 |
+-------------------+------------------+--------+
When viewed from the operator table, there are 2 data with the same operator_id that is unreadable
+-------------+------------------+
| OPERATOR_ID | NAMA_LENGKAP |
+-------------+------------------+
| 1 | Muhammad Kusnadi |
| 3 | Lina Harun |
| 5 | Tirto Kusumo |
+-------------+------------------+
You need to include the columns in the SELECT-list t.tanggal_transaksi, o.nama_lengkap, also in the GROUP BY-list but not the others like t.transaksi_id. So, you might use the following without any issue :
SELECT t.tanggal_transaksi, o.nama_lengkap, SUM(td.harga * td.qty) total
FROM transaksi t
INNER JOIN transaksi_detail td ON ( td.transaksi_id = t.transaksi_id )
INNER JOIN operator o ON ( o.operator_id = t.operator_id )
GROUP BY t.tanggal_transaksi, o.nama_lengkap;
Or this one :
SELECT t.transaksi_id, SUM(td.harga * td.qty) total
FROM transaksi t
INNER JOIN transaksi_detail td ON ( td.transaksi_id = t.transaksi_id )
GROUP BY t.transaksi_id;
P.S. Prefer using ANSI-92 JOIN standard rather than old-style comma-type JOIN.

SQL SELECT JOIN FILTER

I try to explain the problem as good as possible.
I have multiple tables:
project, group, period.
The connection table of these three is called project_status.
I will quickly show there content
Project
| projectID | name | date |
| ------------------------|
| 1 | test | 2015 |
| 2 | test | 2015 |
Group
| groupID| name |
| --------------|
| 1 | ab |
| 2 | cd |
Period
| periodID | status |
| ---------------------|
| 1 | 0 | #inactive
| 2 | 1 | #active
| 3 | 2 | #new
Project stats
| projectID | groepID | periodID |
| -------------------------------|
| 1 | 1 | 2 | #active period
| 1 | 1 | 3 | #new period
Now in a gui you can select a period. Is the period active then i dont show the
project because it's in use (active). Now when i select a period with status new there must be a check to determine:
Is this project already in a new period
The problem is when i write a query there is always the active period. How could i write a query that only checks in project status for status new
i have tried the following query
SELECT projectID, name
FROM project
WHERE projectID IN
(
SELECT ps.projectID
FROM project_status as ps
JOIN period as per
ON ps.periodID = per.periodID
WHERE per.status = 0
AND per.stats != 2
)
OR projectID NOT IN
(
SELECT projectID
FROM project_status
)
Your query looks right.
Only remove
AND per.periode_status != 2
What is periode_status ? You didnt explain
WHERE per.status = 0
AND per.periode_status != 2 -- remove it
You could use a cross apply, something like this would select projectID & name where periodID = 3:
SELECT projectID, name FROM project a
CROSS APPLY (SELECT projectID,periodID FROM project_status WHERE projectID = a.projectID) b
WHERE b.periodID = 3