Mysql select row containing string + specific int column comparison - javascript

I have found numerous questions related to mine but still can't solve this issue.
In my table there are 3 columns filled with integer values and 3 columns with string values. I have several rows.
Table structure example:
INT_1 | INT_2 | INT_3 | VALUE1 | VALUE2 | VALUE3
33 | 25 | 10 | "nice"| "hello"| "goodbye"
---------------------------------------------------
10 | 15 | 28 | "dice"| "hay" | "bird"
I have a string that I use to select the rows based on the VALUE columns. The way I want to select it is with inclusion which means if the string is "llo" I should get the row where at least one of the values (VALUE,VALUE2,VALUE3) contains "llo" (would select the row with "hello" in VALUE2, for example).
However if two different rows have VALUE columns that contain the string (like in the example if the string is "ice") I want to retrieve the row where the INT column associated to that VALUE is higher. In the example since the string was compared to VALUE1 I should compare INT_1 of the upper column with INT_1 of the lower column and retrieve the row where INT_1 is higher. (INT_1 -> VALUE1, INT_2 -> VALUE2, INT_3 -> VALUE3).
Well not much but I could figure this myself:
SELECT * FROM my_table WHERE VALUE1 = "+string+" OR VALUE2= "+string+" OR VALUE3= "+string+"";
I am not sure how should I include "LIKE" to check for containing string when I have the values like "+string+".
I don't know how to compare the specific INT column with the specific VALUE column when I have more than one row where VALUE contains the string.

First normalize your table using UNION ALL. That means every row have to be splitted into three. One for each group (INT_1 VALUE1, INT_2 VALUE2, INT_3 VALUE3). Since you don't have an explicit primary key, you need to include all columns to identify the source row.
select t.*, 1 as position, INT_1 as i, VALUE1 as v from my_table t
union all
select t.*, 2 as position, INT_2 as i, VALUE2 as v from my_table t
union all
select t.*, 3 as position, INT_3 as i, VALUE3 as v from my_table t
Result:
| INT_1 | INT_2 | INT_3 | VALUE1 | VALUE2 | VALUE3 | position | i | v |
|-------|-------|-------|--------|--------|---------|----------|----|---------|
| 33 | 25 | 10 | nice | hello | goodbye | 1 | 33 | nice |
| 10 | 15 | 28 | dice | hay | bird | 1 | 10 | dice |
| 33 | 25 | 10 | nice | hello | goodbye | 2 | 25 | hello |
| 10 | 15 | 28 | dice | hay | bird | 2 | 15 | hay |
| 33 | 25 | 10 | nice | hello | goodbye | 3 | 10 | goodbye |
| 10 | 15 | 28 | dice | hay | bird | 3 | 28 | bird |
http://sqlfiddle.com/#!9/9086d5/1
Now put it in a subquery and search for your string in the v column using WHERE v LIKE '%ice%'.
select *
from (
select t.*, 1 as position, INT_1 as i, VALUE1 as v from my_table t
union all
select t.*, 2 as position, INT_2 as i, VALUE2 as v from my_table t
union all
select t.*, 3 as position, INT_3 as i, VALUE3 as v from my_table t
) n
where v like '%ice%'
Result:
| INT_1 | INT_2 | INT_3 | VALUE1 | VALUE2 | VALUE3 | position | i | v |
|-------|-------|-------|--------|--------|---------|----------|----|------|
| 33 | 25 | 10 | nice | hello | goodbye | 1 | 33 | nice |
| 10 | 15 | 28 | dice | hay | bird | 1 | 10 | dice |
http://sqlfiddle.com/#!9/9086d5/4
Last step - Pick the row with the highest value in i using ORDER BY i DESC LIMIT 1:
select `INT_1`, `INT_2`, `INT_3`, `VALUE1`, `VALUE2`, `VALUE3`
from (
select t.*, 1 as position, INT_1 as i, VALUE1 as v from my_table t
union all
select t.*, 2 as position, INT_2 as i, VALUE2 as v from my_table t
union all
select t.*, 3 as position, INT_3 as i, VALUE3 as v from my_table t
) n
where v like '%ice%'
order by i desc
limit 1
Result:
| INT_1 | INT_2 | INT_3 | VALUE1 | VALUE2 | VALUE3 |
|-------|-------|-------|--------|--------|---------|
| 33 | 25 | 10 | nice | hello | goodbye |
http://sqlfiddle.com/#!9/9086d5/5
The query can be shorter if you use a HAVING clause instead of WHERE, so you don't need to use a subquery. But then you get two columns (i and v), that you might not need. On the other hand, they might be the only columns you need.
select t.*, INT_1 as i, VALUE1 as v from my_table t union all
select t.*, INT_2 as i, VALUE2 as v from my_table t union all
select t.*, INT_3 as i, VALUE3 as v from my_table t
having v like '%ice%'
order by i desc
limit 1
And one more modification which might improve the performance a little bit:
select t.*, INT_1 as i from my_table t where VALUE1 like '%ice%' union all
select t.*, INT_2 as i from my_table t where VALUE2 like '%ice%' union all
select t.*, INT_3 as i from my_table t where VALUE3 like '%ice%'
order by i desc
limit 1

This is a horrible data structure. But here is one way to do this?
SELECT t.*
FROM my_table t
WHERE VALUE1 LIKE '%string%' OR VALUE2 LIKE '%string%' OR VALUE3 LIKE '%string%'
ORDER BY greatest( (case when VALUE1 LIKE '%string%' then int_1 else -1 end),
(case when VALUE1 LIKE '%string%' then int_2 else -1 end),
(case when VALUE1 LIKE '%string%' then int_3 else -1 end) ) desc
LIMIT 1;

Related

Automatically increment value by search /compare and match two columns in Google Sheets Script

I currently have to manually enter Sheet1 column B, but I'd like to auto increment it every time the script runs.
I am using a Google Sheets script.
This part is working.
How it works:
Sheet2 column A is a drop down list imported from Sheet1 column A
if Sheet2 column B is anniversary of todays date Sheet 2 column F is automated to be 'reset'
the working script then deletes the rows in Sheet 2 where F is 'reset' and adds new rows for each to the bottom
Currently using this script
function writeupReset() {
var ss = SpreadsheetApp.getActiveSpreadsheet();
var s = ss.getSheetByName('Sheet2');
var r = s.getRange('C:C');
var v = r.getValues();
for(var i=v.length-1;i>=0;i--){
if(v[0,i]=='reset'){
s.insertRowsAfter(251,1);
s.deleteRow(i+1);
}
}
}
Example of the working bits using todays date - 6/2/20
Sheet1 Sheet2 (before script) Sheet2 (after script)
A B A B C A B C
|---------------| |-------------------------| |-------------------------|
1 | name | resets | 1 | name | date | delet | 1 | name | date | delet |
|---------------| |-------------------------| |-------------------------|
2 | bill | 1 | 2 | bill | 6/2/19 | reset | 2 | alex | 9/5/19 | |
|---------------| |-------------------------| |-------------------------|
3 | mark | 5 | 3 | alex | 9/5/19 | | 3 | adam | 11/6/19 | |
|---------------| |-------------------------| |-------------------------|
4 | holy | 2 | 4 | adam | 11/6/19 | | 4 | tony | 12/1/19 | |
|---------------| |-------------------------| |-------------------------|
5 | tony | 0 | 5 | mark | 6/2/19 | reset | 5 | | | |
|---------------| |-------------------------| |-------------------------|
6 | alex | 2 | 6 | tony | 12/1/19 | | 6 | | | |
|---------------| |-------------------------| |-------------------------|
7 | june | 1 | 7 | | | | 7 | | | |
|---------------| |-------------------------| |-------------------------|
8 | jack | 0 | to 252 rows (last two hidden) to 252 rows (last two hidden)
|---------------|
9 | adam | 2 |
|---------------|
So how can I edit the script to automatically increment Sheet1 column B when the script deletes those 'reset' rows in Sheet1?
I believe your goal as follows.
You want to increase the values of the column "B", that the name is the same , in "Sheet1" when the rows with reset in "Sheet2" are deleted by the script.
In your case, the same names are included in the column "A" in "Sheet2".
You want to achieve this by modifying your script in your question.
For this, how about this answer?
Modification points:
In this case, it is required to know the values of "Sheet1" and compare them with the values of "Sheet2". The flow is as follows.
Delete rows in "Sheet2".
At that time, an object including the information of the deleted rows is created.
Increase values of the column "B" in "Sheet1".
The values of the column "B" are updated using the object, and the updated values are put to the sheet.
When above points are reflected to your script, it becomes as follows.
Modified script:
function writeupReset() {
var ss = SpreadsheetApp.getActiveSpreadsheet();
// 1. Delete rows in Sheet2.
var s = ss.getSheetByName('Sheet2');
var r = s.getRange('A1:C' + s.getLastRow()); // Modified
var v = r.getValues();
var obj = {}; // Added
for(var i=v.length-1;i>=0;i--){
if(v[i][2] == 'reset') { // Modified
s.insertRowsAfter(251,1);
s.deleteRow(i+1);
var name = v[i][0] // Added
obj[name] = obj[name] ? obj[name] + 1 : 1; // Added
}
}
// I added below script.
// 2. Increase values of the column "B" in Sheet1.
var sheet = ss.getSheetByName("Sheet1");
var range = sheet.getRange("A2:B" + sheet.getLastRow());
var values = range.getValues().map(([a, b]) => ([obj[a] ? b += obj[a] : b]));
range.offset(0, 1, values.length, 1).setValues(values);
}
Note:
In this modified script, it supposes that each value of the column "A" in "Sheet1" is the unique value in all values. From your question, I could understand like this.
If the sheet names of "Sheet1" and "Sheet2" are different from your actual situation, please modify them.
If your actual situation is different from the structure of your sample values in your question, this modified script might not work. So please be careful this.
References:
map()
setValues(values)

posgresql: Selecting specific column in an existing table and sort it according to absolute values in descending order?

I have the following table:
+----------+----------+---------+----------+----------+----------+
| Date | A | B | C | P | D |
+----------+----------+---------+----------+----------+----------+
|2019-01-10| -111,000 | 666,000 | 78,000 | 45 | 120,000 |
|2019-01-09| 555,000 | 55,000 | 100,000 | 55 | 700,000 |
|2019-01-08| 48,000 | 30,000 | 40,000 | 65 | 450,000 |
|2019-01-07| 600,000 |-450,000 | -800,000 | 90 | 980,000 |
+----------+----------+---------+----------+----------+----------+
May I know how to create a temporary table from the existing table above to become the table as below:
+----------+----------+---------+----------+----------+
| Date |Components| Values | Comp_no | P |
+----------+----------+---------+----------+----------+
|2019-01-10| A |-111,000 | 1 | 45 |
|2019-01-10| B | 666,000 | 2 | 45 |
|2019-01-10| C | 78,000 | 3 | 45 |
+----------+----------+---------+----------+----------+
Then sort it according to absolute values as below:
Give numbers to the largest value as '1', 2nd largest as '2' and so on.
The sorted_comp_no represents the order whereby the components is sorted where '1' is 'B', '2' is A and '3' is C.
+----------+----------+---------+----------+----------+--------------+
| Date |Components| Values | comp_no | P | sort_sequence|
+----------+----------+---------+----------+----------+--------------+
|2019-01-10| A |-111,000 | 1 | 45 | 2 |
|2019-01-10| B | 666,000 | 2 | 45 | 1 |
|2019-01-10| C | 78,000 | 3 | 45 | 3 |
+----------+----------+---------+----------+----------+--------------+
Use the comp_no and sort.
The components are now sorted according to their values.
+----------+----------+---------+----------+----------+--------------+
| Date |Components| Values | comp_no | P |sorted_comp_no|
+----------+----------+---------+----------+----------+--------------+
|2019-01-10| B | 666,000 | 2 | 45 | 2 |
|2019-01-10| A |-111,000 | 1 | 45 | 1 |
|2019-01-10| C | 78,000 | 3 | 45 | 3 |
+----------+----------+---------+----------+----------+--------------+
I've already created the temporary table template but still stuck in taking the name of specific column only (A,B and C) to be put into a column of its own category ignoring column D . Column P is brought into the temporary table but remain as is. There is also a dependency to the date column as there are multiple data of different date.
But the end goal is to be able to "sort specific column according to its absolute value at a specific date dynamically".

Split joined result set to rows

Have a stored procedure which process records from certain tables. To store some result generated by join operation there is a temporary table.
Table A
+----+------+--------+
| id | name | number |
+----+------+--------+
| 1 | John | 123 |
| 2 | Tim | 567 |
| 3 | Bill | 789 |
| 4 | Jim | 345 |
+----+------+--------+
Table B
+----+------+--------+
| id | code | number |
+----+------+--------+
| 1 | LK | 123 |
| 2 | CN | 123 |
| 3 | BN | 789 |
| 4 | IN | 345 |
+----+------+--------+
Table Temp
+----+------+-----+------+--------+
| id | name | age | code | number |
+----+------+-----+------+--------+
| 1 | John | 54 | LK | 123 |
| 1 | John | 54 | CK | 123 |
| 3 | Bill | 26 | BN | 789 |
| 4 | Jim | 78 | IN | 345 |
+----+------+-----+------+--------+
Converted the table Temp result set to JSON.
[{"id":1,"name":"John","code":"LK","number":123}, {"id":2,"name":"John","code":"CK","number":123}, {"id":3,"name":"Bill","code":"BN","number":789}, {"id":4,"name":"Jim","code":"IN","number":345}]
I need to split the records to show it on view as below.
+------------+-----+------+--------+
| name | age | code | number |
+------------+-----+------+--------+
| John | 54 | | |
| | | LK | 123 |
| | | CK | 123 |
| Bill | 26 | | |
| | | BN | 789 |
| Jim | 78 | | |
| | | IN | 345 |
+------------+-----+------+--------+
[{"name":"John","age":54}, {"code":"LK","number":123}, {"code":"CK","number":123}, {"name":"Bill","age":26}, {"code":"BN","number":789}, {"name":"Jim","age":78}, {"code":"IN","number":345}]
What is an effective way, split the JSON or is it possible to generate such result set by querying table Temp in MySQL?
-- query wanted
select
if(name = #last_name, '', #last_name := name) as name,
if(age = #last_age, '', #last_age := age) as age,
code,
number
from
(
(select name, age, code, number from t)
union
(select distinct name, age, '', '' from t)
order by 1,2,3,4
) as t2 cross join (select #last_name := null, #last_age := null ) param;
Demo:
SQL:
-- data
create table t(id int, name char(20), age int, code char(20), number int);
insert into t values
( 1 , 'John' , 54 , 'LK' , 123 ),
( 1 , 'John' , 54 , 'CK' , 123 ),
( 3 , 'Bill' , 26 , 'BN' , 789 ),
( 4 , 'Jim' , 78 , 'IN' , 345 );
select * from t;
-- query wanted
select
if(name = #last_name, '', #last_name := name) as name,
if(age = #last_age, '', #last_age := age) as age,
code,
number
from
(
(select name, age, code, number from t)
union
(select distinct name, age, '', '' from t)
order by 1,2,3,4
) as t2 cross join (select #last_name := null, #last_age := null ) param
;
Output:
mysql> select * from t;
+------+------+------+------+--------+
| id | name | age | code | number |
+------+------+------+------+--------+
| 1 | John | 54 | LK | 123 |
| 1 | John | 54 | CK | 123 |
| 3 | Bill | 26 | BN | 789 |
| 4 | Jim | 78 | IN | 345 |
+------+------+------+------+--------+
4 rows in set (0.00 sec)
mysql> -- query wanted
mysql> select
-> if(name = #last_name, '', #last_name := name) as name,
-> if(age = #last_age, '', #last_age := age) as age,
-> code,
-> number
-> from
-> (
-> (select name, age, code, number from t)
-> union
-> (select distinct name, age, '', '' from t)
-> order by 1,2,3,4
-> ) as t2 cross join (select #last_name := null, #last_age := null ) param
-> ;
+------+------+------+--------+
| name | age | code | number |
+------+------+------+--------+
| Bill | 26 | | |
| | | BN | 789 |
| Jim | 78 | | |
| | | IN | 345 |
| John | 54 | | |
| | | CK | 123 |
| | | LK | 123 |
+------+------+------+--------+
7 rows in set (0.00 sec)
To me this seems more like a formatting the output question, rather than how to query the database, so I would rather use js on the client side to format the output in this way.
If I really wanted to use sql, then honestly, I would not use the temp table. I would rather create another query based on the 2 original tables with a union and order the final resultset. All you would have to do on the client side is to hide the id column:
(select id, name, age, null as code, null as number
from a)
union
(select id, null, null, code, number
from b)
order by id asc, name desc

Javascript Sum Distinct Rows into a input jqueryDatatables

I have a tables filled with data using Jquery Datatables, what i want is to be able to sum all data from the distinc values of a column but when a dropdownlist value is changed and save the sum value into a new Html Input with Javascript Example:
I got my table filled with data like this:
|Platillo | PDV | Precio | Can | Date |
------------------------------------------------------------------
| Poz | REST | 40 | 2 | 01/02/2016|
------------------------------------------------------------------
| Tor | REST | 50 | 2 | 02/02/2016|
------------------------------------------------------------------
| Zes | REST | 100 | 2 | 01/02/2016|
------------------------------------------------------------------
| Poz | FUEM | 60 | 2 | 01/02/2016|
------------------------------------------------------------------
| Tor | FUEM | 70 | 2 | 01/02/2016|
------------------------------------------------------------------
| Zes | FUEM | 120 | 2 | 01/02/2016|
------------------------------------------------------------------
| Poz | VTSI | 45 | 2 | 02/02/2016|
------------------------------------------------------------------
| Tor | VTSI | 57 | 2 | 01/02/2016|
------------------------------------------------------------------
| Zes | VTSI | 10 | 2 | 02/02/2016|
------------------------------------------------------------------
i want is to be able to sum all the values from the column 'Precio' into a 'Html Input Field' but i want to sum the totals of each distinct value from column 'PDV', and triggered by the value of a dropdown list,
Ex: if user select's Date '01/02/2016' i shoul fil my html Inputs with the sum of the data of all distinct value of column 'PDV' but only when they match the Date selected by the user '01/02/2016' looking for this output:
<option value="">Todos</option>
<option value="01/02/2016">#item</option> // USER SELECTS THIS VALUE
<option value="02/02/2016">#item</option>
My input field are like follow:
<input value="//TOTAL SUM FROM REST WHERE DATE IS EQUAL AS UsER SELECT '01/02/2016'" />
<input value="//TOTAL SUM FROM REST WHERE DATE IS EQUAL AS UsER SELECT '01/02/2016'" />
<input value="//TOTAL SUM FROM REST WHERE DATE IS EQUAL AS UsER SELECT '01/02/2016'" />
Im new to javascript and right now i have only be able to filter my Datatable based on the selected date but i need to sum all distincs values of my 'PDV' column each time user selects a date value how can i do it?
UPDATED:
i have the code of my dropdown filter y just need to know how to sum columns based on unique column items on my search javascript
This is my search code:
$('#sel0').on('change', function () {
dataTable.columns('.fechas').search(this.value).draw();
var datafecha = $(this).val();
});
You need to write a custom filter. Or take a look at this below to get an idea :
var val = $.fn.dataTable.util.escapeRegex($('dropdown').val());
column.search( val ? '^'+val+'$' : '', true, false ).draw();
var sum = column.data().unique().sum();
alert(sum);

Ext JS 4 : GridPanel - Update a column cell values based on the updated cell

I have a grid panel showing article details. There are several columns. When our an employee change the one of cell value, I want to match all column field values based on the updated field.
+----------------------------------------+
| ROW ID | COL A | COL B | COL C | COL D |
+----------------------------------------+
| 1 | TR | IST | 100 | 12 |
+----------------------------------------+
| 2 | US | NY | 60 | 7 |
+----------------------------------------+
| 3 | DE | BER | 74 | 9 |
+----------------------------------------+
What I want to do, when user change the ROW-1 COL D value (12) with 15, the other rows COL D values should change automatically with 15.
+----------------------------------------+
| ROW ID | COL A | COL B | COL C | COL D |
+----------------------------------------+
| 1 | TR | IST | 100 | 15 | <- user has changed the value
+----------------------------------------+
| 2 | US | NY | 60 | 15 |
+----------------------------------------+
| 3 | DE | BER | 74 | 15 |
+----------------------------------------+
Updates your records in the edit event of the grid.
Here's an example:
Ext.widget('grid', {
renderTo: Ext.getBody()
,columns: [{dataIndex: 'a', header: 'Col A', editor: 'textfield'}]
,store: {
fields: ['a']
,data: [{a: 1},{a:2},{a:3}]
}
,plugins: [
Ext.create('Ext.grid.plugin.CellEditing', {
clicksToEdit: 1
})
]
,listeners: {
// this event is added to the grid by the CellEditing plugin
edit: function(editor, e) {
e.grid.getStore().each(function(record) {
record.set('a', e.value);
});
}
}
});
You should update the records in the store behind.
Something like
store.each(function(record){
record.set('col_d', 15);
});

Categories

Resources