I have table images with ID's starting from 1 to 5000. On the page they are showed straight from 1 to 5000. What I wonder is it possible to scramble the records inside database table not to query them by RAND() on the page because they will be random on every refresh. I don't want this.
For example id(1) to become id(343).. id(453)->id(4444) and so on.. just scrambling them.
UPDATE:
This is the query which I'm trying
alter table images add column randorder double;
update table images
set randorder = rand();
create index idx_table_randorder on table(randorder);
When is executed I got column randorder with NULL but the query return again
1064 - You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'table images set randorder = rand()' at line 1
How about this?
alter table add column randorder double;
update table
set randorder = rand();
create index idx_table_randorder on table(randorder);
Then you can "shuffle" the records by doing:
select t.*
from table t
order by randorder;
This will use the index so it will be fast. It is stable, so it will work by paging. When you want to change the ordering, you can use the update.
Save the rows into an array. Then run:
shuffle($array);
See http://php.net/manual/en/function.shuffle.php
Related
I have a performance issue when working with a huge table
I add index on column using this :
ALTER table add index column;
and on the text/blob column :
alter table add index (cat(200));
My table has about 6M rows and i am working with InnoDB engine (Mysql 5.5)
This query is very fast now that i add index on "order by" column:
SELECT * from table order by column DESC LIMIT 0,40
But when I add a WHERE clause on this query its very slow and it take about 10 seconds to load even with the column "cat" index like above. //index instead of indexed
SELECT * from table WHERE cat = 'electronic' order by column DESC LIMIT 0,40
the EXPLAIN of this slow query :
EXPLAIN SELECT * from table WHERE cat = 'electronic' order by 'id' DESC LIMIT 0,40
id : 1
select_type : SIMPLE
table : product
type : ref
possible_keys: cat
key: cat
Key_len: 203
ref: const
row : 1732184
extra: using where
The query working fine with small table with 50k rows but with 6M rows its slow. Why?
Do not use prefixing, such as cat(200); it usually makes the index unusable. I have never seen a case where the Optimizer, when faced with INDEX(a(10), b), gets past a and makes any use of b.
Change cat to be VARCHAR(255). That is probably more than sufficient for "categories".
The best index (if it is possible) is
INDEX(cat, `column`)
Note that cat is in the WHERE with =. It handles the entire WHERE, so the index can move on to the ORDER BY. Hence column can be used, too. More discussion of index making .
If cat must be TEXT, then the best you can do is
INDEX(`column`)
Then the Optimizer may decide to use it for avoiding a filesort. But if there are fewer than 40 (see LIMIT) 'electronic' rows, it will take an big scan and probably be slower than not using the index. So, I am not sure that it is even worth having INDEX(column).
For this query:
SELECT t.*
FROM table t
WHERE cat = 'electronic'
ORDER BY column DESC
LIMIT 0, 40;
The best index is a composite index on table(cat, column). You can use a prefix if column is too wide: table(cat, column(200)).
The best option is to index the table, if you dont know how to do it, you can check this doc
So, when you perform the query, the mysql will start searching on the indexed values, skipping a lot of useless data for that request.
I have two main tables:
Products
Category
Then I have a 3rd many-to-many table called Prices with the rows:
IdProducts (Primary key and Foreign Key from Products)
IdCategory (Primary key and Foreign Key from Category)
Price
The 3rd table doesn't have an individual ID for each row, just those 3 rows.
That said, I've already been able to insert data with no problems on the 3rd table using the data from Products and Category. Now I'm trying to edit this data in a small program but I just can't get if there is a coincidence to pre-fill the edit form. I'm using the following code:
$sql1 = mysqli_query($con,"SELECT * FROM table3 WHERE (idProducts='$variable1' AND idCategory='$variable2') LIMIT 1") or die(mysql_error());
$PriceCount = mysqli_num_rows($sql1);
if($productCount>0){
while($row = mysqli_fetch_array($sql1)){
$priceshow= $row["price"];
$idCategoryshow= $row["idCategory"];
$idProductshow= $row["idProduct"];
}
}
So with that I could get the price, category id, and product id ready to show in html.
I don't know if I'm doing something really wrong but my best bet is that the error is in the MySql query:
"SELECT * FROM table3 WHERE (idProduct='$variable1' AND idCategory='$variable2') LIMIT 1"
This returns no values even if I send data that I know it should be using.
Is that how I'm supposed to try to get all the rows? Or maybe something like this can't be done and I need an individual ID for the prices?
EDIT: I found a dirty work around by sending the variables on a href Link... anyway Im facing the almost very same problem when trying to update the desired row, mysql code for update is this:
"UPDATE table3 SET (price1='$var1' AND price2='$var2') WHERE (price.idProduct='$idProduct' AND price.idCategory='$idCategory') "
and i recieve the following error
You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'SET (price='123231211.00' AND price='1212654.00') WHERE (table3.idProduct='QEW21' AND ta' at line 1
Finally I can go to sleep xd
"UPDATE table3 SET price1='$var1', price2='$var2' WHERE
price.idProduct='$idProduct' AND price.idCategory='$idCategory'"
I was using "SET(X AND Y)" and "WHERE(X AND Y)" and checking the right uses of AND ends up it was actually like: "SET X, Y" and "WHERE X AND Y"
Why my query fast when I run.
select count(*) as aggregate from `news` where `news`.`deleted_at` is null and `status` = '1'
But, slow when I run.
select count(*) as aggregate from `news` where `news`.`deleted_at` is null and `status` = '1' and `newscategory_id` = '17'
It is my table news structure image, have a look at here.
Sorry because my reputation is less than 8, so I can't attach image.
try adding an composite index on the three columns you are using for your select:
ALTER TABLE news ADD INDEX comp_index (deleted_at, status, newscategory_id);
and check it again.
probably use EXPLAIN to see if any indexes you have are used.
Indexes are used to find rows with specific column values quickly.
Without an index, MySQL must begin with the first row and then read
through the entire table to find the relevant rows. The larger the
table, the more this costs. If the table has an index for the columns
in question, MySQL can quickly determine the position to seek to in
the middle of the data file without having to look at all the data.
This is much faster than reading every row sequentially.
Try to add this in your DB:
CREATE INDEX newCategory_indx ON news (newscategory_id)
CREATE INDEX status_indx ON news (status)
This will give you quick result, as compared to previously generate (non-indexed column) result.
To know more about index and it's importance visit here
I want to perform a mysql UPDATE query and then get an array of ids that were effected in the change.
This is my update query
mysql_query("UPDATE table SET deleted='1' WHERE id='$id' OR foo='$foo' OR bar='$bar'");
I know that I can do something like this to get the created id from an INSERT query
mysql_query("INSERT INTO table (id,foo,bar) VALUES ('$id','$foo','$bar')");
$newid = mysql_insert_id();
I don't think MySQL has anything like the OUTPUT or RETURNING clauses that other databases support. You can get the list of ids by running a select before the update:
create table temp_table ids_to_update as
SELECT id
FROM table
WHERE (deleted <> '1' or deleted is null) and *id='$id' OR foo='$foo' OR bar='$bar');
Note that MySQL doesn't do an update when the value doesn't change. Hence the first condition -- which you may or may not find important.
Then, to ensure integrity (in the event of intervening transactions that change the data), you can do:
update table t join
temp_table tt
on t.id = tt.id
set deleted = '1';
You could also wrap the two queries in a single transaction, but I think using a temp table to store the ids is probably easier.
I've finally gotten my queries ready to insert into code but now I'm getting an error when running the whole query. I believe it has to do with the drop table function. I originally had them inline and then read that I should remove it and add at the beginning of the query like so:
$query = $this->db->query("DROP TABLE IF EXISTS resultx;");
$query = $this->db->query("DROP TABLE IF EXISTS resulty;");
$query = $this->db->query("
CREATE TEMPORARY TABLE resultx AS
select *, CONCAT(Credit,'_',OrderStat) as consol from (..........
I am creating two temp tables and then joining them in the last query. I am not sure how to put that second DROP temp table back into the full query or if that's even the right way to go.
The error that I'm getting is:
A Database Error Occurred
Error Number: 1064
You have an error in your SQL syntax;
check the manual that corresponds to your MySQL server version for the right syntax to use
near 'CREATE TEMPORARY TABLE resulty AS select packetDeet,Sales,SaleDate, UserID,Lead' at line 15
Query:
CREATE TEMPORARY TABLE resultx AS
select
*,
CONCAT(Credit,'_',OrderStat) as consol
FROM
( select
packetDetailsId, GROUP_CONCAT(Credit) AS Credit,
GROUP_CONCAT(AccountNum) AS AccountNum,
GROUP_CONCAT(OrderStat) AS OrderStat
FROM
( SELECT
pd_extrafields.packetDetailsId,
CASE WHEN
pd_extrafields.ex_title LIKE ('%Credit%')
THEN pd_extrafields.ex_value
ELSE NULL
END as Credit,
CASE WHEN
pd_extrafields.ex_title LIKE ('%Account%')
THEN pd_extrafields.ex_value
ELSE NULL
END as AccountNum,
CASE WHEN
pd_extrafields.ex_title LIKE ('%Existing%')
THEN pd_extrafields.ex_value
ELSE NULL
END as OrderStat
FROM pd_extrafields
) AS myalias
GROUP BY packetDetailsId
)as TempTab;
CREATE TEMPORARY TABLE resulty AS select packetDeet,Sales,SaleDate, .........
Please let me know if this makes sense or I need to update question with more information.
If you are trying to execute both queries in one call to $this->db->query() the problem is probably that your database library does not permit multiple queries.
To see if that is the problem, you should split them up in two separate queries.