Hello how can i joint table in progress 4gl? And display - openedge

Define variable i as integer no-undo.
For each Sports.customer where Sports.customer.CustNum = 1 AND Sports.Order.OrderDate = 11/21/1997 NO-LOCK.
/* it says Missing for find etc */
I need to display the Order of Lift Tours i used his primary key but im having trouble to access the 2 tables
Tables
Customer PK CustNum
Order PK OrderName FK CustNum
Order-line PK Orderline
I need to display the Orders of Lift Tours with the date order of 11/21/1997 and diplay total price of lift tours
Thanks guys

define variable orderTotal as decimal no-undo.
for each customer no-lock where name = "Lift Tours",
each order no-lock where order.custNum = customer.custNum and order.orderDate = 11/21/1997,
each orderLine no-lock where orderLine.orderNum = order.orderNum:
orderTotal = orderTotal + ( orderLine.Qty * orderLine.price ).
end.
display orderTotal.
The "," is used to join WHERE clauses in the FOR EACH. You specify the common fields to make the join on in those WHERE clauses.

For total price, you'll have to join Order and OrderLine.
DEFINE VARIABLE deTotal AS DECIMAL NO-UNDO.
FOR EACH Order WHERE Order.CustNum = 1 AND Order.OrderDate = 11/21/1997 NO-LOCK,
EACH OrderLine OF Order NO-LOCK:
ASSIGN deTotal = deTotal = deTotal + OrderLine.Qty * OrderLine.Price .
END.

Related

How to subtract two rows from two different selects?

I'm trying to subtract the total number shares for each symbol from the sell orders and the buy orders so I can have that total of shares owned.
buy = db.execute("SELECT symbol,SUM(shares) as total FROM negocios WHERE userid = ? and operation = 'buy' GROUP BY symbol");
sell = db.execute("SELECT symbol,SUM(shares) as total FROM negocios WHERE userid = ? and operation = 'sell' GROUP BY symbol")
I want a table like this with the values already subtracted:
symbol
total
CSCO
25
GOOG
6
NFLX
32
I was trying :
SELECT ((SELECT symbol,SUM(shares) as total FROM negocios WHERE userid = ? and operation = 'buy' GROUP BY symbol) - (SELECT symbol,SUM(shares) as total FROM negocios WHERE userid = ? and operation = 'sell' GROUP BY symbol) AS diff;
But I'm getting an error:
Parse error: sub-select returns 2 columns - expected 1
Table schema:
CREATE TABLE negocios (id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL, userid TEXT NOT NULL, symbol TEXT NOT NULL, operation TEXT CHECK( operation IN ('buy', 'sell')), price DECIMAL(10,2), time TIMESTAMP, shares DECIMAL(10,2), name TEXT);
You can do it with a single query if you use conditional aggregation:
userid = 100 #variable that stores the user's id
sql = """
SELECT symbol,
SUM(shares * CASE operation WHEN 'buy' THEN 1 WHEN 'sell' THEN -1 END) AS total
FROM negocios
WHERE userid = ?
GROUP BY symbol
"""
result = db.execute(sql, (userid,))

SQL query to relate 2 tables

I want to relate following 2 tables in sqlite3. What I understood from other examples is that we should have some common field between each table, so I added order_ID.
1) How to write sqlite queries for creating the relation between these tables?
2) How to manage Table 2, where same order can have multiple products, so order ID is repeated. An order can have min 1 and max 10 products. So it has dynamic range of 1-10.
table 1:
order_ID date buyer ship_chr
001 01/01 abc 15
002 05/01 xyz 10
table 2:
order_ID prod quantity rate
001 pen 50 2
001 paper 25 1
001 pin 50 2
002 paper 25 1
002 pen 100 2
It looks like you want to store orders and information about those orders. First, make an orders table.
create table orders (
id integer primary key autoincrement,
created_at timestamp not null default current_timestamp,
buyer text not null,
ship_chr text not null
)
Note that instead of order_id, the primary key of a table is just id.
It's not required, but it is a convention I like as it keeps primary and foreign keys distinct.
Also note that I'm using the timestamp type to store dates, this will make working with those dates much easier as you can use SQLite date functions.
Now we need a table for information about what is in each order.
create table order_products (
id integer primary key autoincrement,
order_id integer not null references orders(id),
product text not null,
quantity integer not null,
rate integer not null
)
This sets up a one-to-many relationship betweeen orders and order_products.
One order can have many products. You can link these tables together using
a join. Here's how you'd get
the buyer for each product.
select o.buyer, op.product, op.quantity
from order_products op
join orders o on o.id = op.order_id
abc|pen|50
abc|paper|25
abc|pin|50
xyz|paper|25
xyz|pen|100
join orders o on o.id = op.order_id says for every row in order_products find one in orders where order.id matches the row's order_id and treat them both as a single row.
From here you'll probably want to make products and buyer their own tables
as well to store any information about the buyers and products. It also ensures
that the products and buyers exist avoiding typos.
create table buyers (
id integer primary key autoincrement,
name text not null,
address text not null,
phone text not null
);
create table products (
id integer primary key autoincrement,
name text not null,
stock integer not null default 0
);
create table orders (
id integer primary key autoincrement,
created_at timestamp not null default current_timestamp,
buyer_id integer references buyers(id) not null,
ship_chr text not null
);
create table order_products (
id integer primary key autoincrement,
order_id integer not null references orders(id),
product_id integer not null references products(id),
quantity integer not null,
rate integer not null
);
Then you can join everything together to get information about products and buyers.
select b.name, p.name, op.quantity
from order_products op
join orders o on o.id = op.order_id
join buyers b on b.id = o.buyer_id
join products p on p.id = op.product_id
name|name|quantity
abc|pen|50
abc|paper|25
abc|pin|50
xyz|paper|25
xyz|pen|100
SQL Fiddle
If you don't do this now it will be harder to do later.

In SQLite, how to insert an id field in select result?

I know it works with following code in MySQL to achieve such goal:
set #n = 0;
select (#n := #n + 1),test_score from test_score where student_name = 'Gao' and test_subject = 'math'
In SQLite,there is no variable, so how can I implement similar function in SQLite?
Thanks!
Assuming you have an ID field in your test_score table you could just easily add ORDER BY ID ASC to your select query.
CREATE TABLE test_score (ID INTEGER AUTOINCREMENT, student_name TEXT, test_subject TEXT, score TEXT)
SELECT ID, score FROM test_score WHERE student_name='Gao' AND test_subject='math' ORDER BY ID ASC;
NB: by default the query would be ordered by the ID anyway, but in case you would want to switch it to the most recent just replace ASC with DESC

i have two tables student and trainer. i want to get values from student and trainer table based on some condition

i have student and trainer tables :
student table:
student_id (primary key)
name
email
trainer table:
trainer_id
student_id
amount
output has to:
sid name email amount
22 ram r#g 200
34 sam r#f
i want to get (student_id,name,email) from student table and (amount) from trainer table(imp : trainer_id and student_id should match(like sid = 46,tid =78,amount=500) then only the amount has to display value. otherwise amount will display empty but (student_id,name,email) should display)
in trainer table, student_id and trainer_id has to match...based on that amount will come..i mean if we send the select query as "select amount from trainer where student_id= 20 and trainer_id=36...". that column should match for sid and tid
If you do it this way, It wil not show data if amount is empty :
select st.student_id,
st.name,
st.email,
tt.amount
from student_table st, trainer_table tt
where st.student_id = tt.student_id
NVL function lets you substitute a value when a null value is encountered,
so if you do it this way, It wil show data and show 0 instead of null:
select st.student_id,
st.name,
st.email,
(nvl(select tt.amount
from trainer_table tt
where st.student_id = tt.student_id,0))) amount
from student_table st
This can be accomplished with PLSQL. Sorry it is so extensive but I hope it allows you to see the power of PLSQL if you need to manipulate data based on conditionals.
DECLARE
TYPE result_record IS RECORD
( sid NUMBER
, name VARCHAR2(60)
, email VARCHAR2(60)
, amount NUMBER);
CURSOR c IS select st.student_id sid,
st.name name,
st.email email,
tt.amount amount
from student_table st, trainer_table tt
where st.student_id = tt.student_id;
TYPE results_table IS TABLE OF results_record INDEX BY BINARY_INTEGER;
c_rec c%ROWTYPE;
temp_rec RESULTS_RECORD;
results RESULTS_TABLE;
lv_index NUMBER := 0;
BEGIN
OPEN c;
WHILE lv_index <= c%ROWCOUNT LOOP
FETCH c INTO c_rec;
temp_rec.sid := c_rec.sid;
temp_rec.name := c_rec.name;
temp_rec.email := c_rec.email;
temp_rec.amount := c_rec.amount;
results(lv_index) := temp_rec;
lv_index := lv_index + 1;
END LOOP;
CLOSE c;
-- Now we can access and modify our table from inside PLSQL
SELECT * FROM results;
-- Use PLSQL logic to make the table output pretty with '$' and conditionals
FOR i IN results LOOP
dbms_output.put_line(i.sid||' $'||i.amount); -- example for how to access
-- your code here
END LOOP;
END;
/
As always, I hope this gives you some ideas.
-V

SQLite: Loop over SELECT statement, replacing the WHERE clause

I have following two tables:
CREATE TABLE messages (
id integer UNIQUE NOT NULL,
message text,
recipient integer NOT NULL,
sender integer NOT NULL,
sent_at text NOT NULL,
FOREIGN KEY (recipient) REFERENCES users (id),
FOREIGN KEY (sender) REFERENCES users (id)
);
CREATE TABLE users (
id integer UNIQUE NOT NULL,
username text NOT NULL,
);
I need a very specific query, that looks like the following:
SELECT *
FROM messages
WHERE sender = 123 OR recipient = 123
ORDER BY id desc
LIMIT 1
I need to kind of iterate over the messages table, using every user, and putting him in the WHERE statement.
-- TABLE 'users':
-- 123 = id of user1
-- 456 = id of user2
-- 789 = id of user3
Is it possible to iterate in SQLite?
Goal is, to get the newest "conversation" for every user in the users table. For every user, the newest message involving him should be displayed, no matter if that newest message was sent or recieved by him.
You could use a correlated subquery to get that value for each user ID:
SELECT id,
username,
(SELECT MAX(id)
FROM messages
WHERE sender = users.id
OR recipient = users.id
) AS last_message_id
FROM users
This is also possible with GROUP BY.
First join the two table together, then create a group for each user:
SELECT users.id,
MAX(messages.id)
FROM users
JOIN messages ON users.id = messages.sender OR
users.id = messages.recipient
GROUP BY users.id
SELECT year , COUNT(*) AS Count
FROM Movie
WHERE Movie.MID NOT IN
(SELECT DISTINCT m.MID
FROM Movie m
JOIN M_Cast m_c ON m.MID = m_c.MID
JOIN Person p_1 ON m_c.PID = p_1.PID
AND p_1.Gender='Male')
AND Movie.MID IN
(SELECT DISTINCT m.MID
FROM Movie m
JOIN M_Cast m_c ON m.MID = m_c.MID
JOIN Person p_1 ON m_c.PID = p_1.PID
AND p_1.Gender='Female')
GROUP BY year;

Resources