How do I combine two UPDATE statements in one MySQL query? - mysql

Greetings,
How would one go about performing two UPDATE statements in one query, for example:
UPDATE albums SET isFeatured = '0' WHERE isFeatured = '1'
combined with
UPDATE albums SET isFeatured = '1' WHERE id = '$id'
Basically, when a new album is featured, the previously featured album is switched back to normal and the newly featured one is set to active.
Thanks!

Try this:
UPDATE albums SET isFeatured = IF(id!='$id', '0','1')

When you have to do this sort of thing it is an indicator that your data model is wrong and could do with some fixing.
So, I'd recommend to add a seperate table featured_albums (FK: int id_album) and use that to determine if the album is featured.
Your update becomes
DELETE FROM featured_album; INSERT INTO featured_album SET id_album = $id;
When selecting join the tables
SELECT album.id,
album.name,
( id_album IS NOT NULL ) AS isfeatured
FROM album
LEFT JOIN featured_album ON id_album = album.id
As requested to expand on the above basically I'm suggesting adding a table that will contain a row indicating the currently selected album. This is a 1 to 1 relationship, i.e. one record in the album table has one related record in the feature_albums table. See Types of Relationship.
You remove the isFeatured field from the album table and add a new table.
CREATE TABLE `featured_album` (
`id_album` INTEGER NOT NULL,
FOREIGN KEY (id_album) REFERENCES `album` (`id`)
);
The DELETE FROM .. INSERT INTO line sets the featured album by creating an entry in the table.
The SELECT statement with the LEFT JOIN will pull in the records from the album table and join those that match from the featured_album table, in our case only one record will match so as there is one field in the featured_album table it will return NULL for all records except the featured album.
So if we did
SELECT album.id, album.name, featured_album.id_album as isFeatured0
FROM album
LEFT JOIN featured_album ON id_album = album.id
We'd get something like the following:
+----+----------------+------------+
| id | name | isFeatured |
+----+----------------+------------+
| 1 | Rumours | NULL |
| 2 | Snowblind | NULL |
| 3 | Telegraph road | 3 |
+----+----------------+------------+
i.e. a NULL for isFeatured or an ID.
By adding the ( id_album IS NOT NULL ) AS isfeatured and using the first query we get
+----+----------------+------------+
| id | name | isfeatured |
+----+----------------+------------+
| 1 | Rumours | 0 |
| 2 | Snowblind | 0 |
| 3 | Telegraph road | 1 |
+----+----------------+------------+
i.e. 0/1 for isfeatured which makes things more readable, although if you're processing the results in PHP it won't make a difference to your code.

You can use CASE WHEN statement and remember to set original value where necessary (ELSE clause below) and order CASE conditions as required (in statement below isFeatured will be 0 if row having requested id also has isFeatured = 1, to change it swap WHEN clauses).
UPDATE albums
SET isFeatured = CASE
WHEN isFeatured = '1' THEN '0'
WHEN id = '$id' THEN '1'
ELSE isFeatured
END

You just can't. You can only select one group of records that should be updated and can then only perform one operation on all of them. It's not possible to do
UPDATE x SET col1 = 1 WHERE col1 = 0 AND col1 = 0 WHERE col1 = 1;
Be careful when using functions to work around this, as they need to be evaluated for every row and this can become really expensive.

MySQL is unable to use the index when it is inside an if function:
You need an index on the function which is not possible in MySQL.
see also: How does one create an index on the date part of DATETIME field in MySql
I am using the employee test database http://dev.mysql.com/doc/employee/en/employee.html
mysql> describe employees;
+------------+---------------+------+-----+---------+-------+
| Field | Type | Null | Key | Default | Extra |
+------------+---------------+------+-----+---------+-------+
| emp_no | int(11) | NO | PRI | NULL | |
| birth_date | date | NO | | NULL | |
| first_name | varchar(14) | NO | | NULL | |
| last_name | varchar(16) | NO | | NULL | |
| gender | enum('M','F') | NO | | NULL | |
| hire_date | date | NO | | NULL | |
+------------+---------------+------+-----+---------+-------+
6 rows in set (0.01 sec)
mysql> select count(*) from employees;
+----------+
| count(*) |
+----------+
| 300024 |
+----------+
1 row in set (0.37 sec)
Set all genders to male so it mimics the question.
mysql> update employees set gender = 'M';
Query OK, 1 row affected (9.11 sec)
Rows matched: 300024 Changed: 1 Warnings: 0
mysql> select emp_no, gender from employees order by emp_no limit 2;
+--------+--------+
| emp_no | gender |
+--------+--------+
| 10001 | M |
| 10002 | M |
+--------+--------+
2 rows in set (0.00 sec)
Set one employee to female.
(Notice it uses the index and is almost instant.)
mysql> update employees set gender = 'F' where emp_no = 10001;
Query OK, 1 row affected (0.14 sec)
Rows matched: 1 Changed: 1 Warnings: 0
Now we use the suggested answer. (Notice it does not use the index and touches every row.)
mysql> update employees set gender = if(emp_no=10002, 'F', 'M');
Query OK, 2 rows affected (10.67 sec)
Rows matched: 300024 Changed: 2 Warnings: 0
Will an index help?
> mysql> create index employees_gender_idx on employees(gender);
Query OK, 300024 rows affected (21.61 sec)
Records: 300024 Duplicates: 0 Warnings: 0
> mysql> update employees set gender = if(emp_no=10001, 'F', 'M');
Query OK, 2 rows affected (9.02 sec)
Rows matched: 300024 Changed: 2 Warnings: 0
Nope.
It was also said that MySQL is only going to look at the rows that need to be changed.
mysql> update employees set gender = 'M';
Query OK, 1 row affected (8.78 sec)
Rows matched: 300024 Changed: 1 Warnings: 0
Guess not. What if use a WHERE clause?
mysql> update employees set gender = 'M' where gender ='F';
Query OK, 0 rows affected (0.03 sec)
Rows matched: 0 Changed: 0 Warnings: 0
Gee that fast, now it used the index.
Mysql has no idea what the IF function will return and must do a full table scan. Notice that WHERE really does mean where and SET really does mean set. You can't expect the DB to just arrange all your clauses to get good performance.
The correct solution is to issue two updates (which if use indexes will be almost instant.)
Notice, it was said elsewhere that MySQL will magically know only update the rows it needs to change.

Adding an alternate method to the excellent answer provided by
#too where instead of CASE IF statement is used -
UPDATE album
-> SET isFeatured = IF (
-> isFeatured = '1', '0', IF (
-> id = '$id', '1', isFeatured
-> ));

I don't think you can, or at least not in a neat or practical way.
If you're wanting to do one call from php/whatever then you can seperate them with semicolons thus:
UPDATE albums SET isFeatured = '0' WHERE isFeatured = '1';UPDATE albums SET isFeatured = '1' WHERE id = '$id';

Related

Target table cannot be same one for update clause in mysql

I have a table name named 'employee'. Table creation code given below:
create table employee(name varchar(50),ph_no varchar(10),e_id varchar(5),pay_scale varchar(5),year varchar(4));
The table content is like below:
insert into employee(name,ph_no,pay_scale,year) values('AMIT','123456','PL-10','2019');
insert into employee(name,ph_no,pay_scale,year) values('AMIT','123456','PL-10','2020');
insert into employee(name,ph_no,pay_scale,year) values('AMIT','123456','PL-11','2021');
insert into employee(name,ph_no,pay_scale,year) values('AMIT','123456','PL-11','2022');
+------+--------+------+-----------+------+
| name | ph_no | e_id | pay_scale | year |
+------+--------+------+-----------+------+
| AMIT | 123456 | NULL | PL-10 | 2019 |
| AMIT | 123456 | NULL | PL-10 | 2020 |
| AMIT | 123456 | NULL | PL-11 | 2021 |
| AMIT | 123456 | NULL | PL-11 | 2022 |
+------+--------+------+-----------+------+
Now I want to update 'e_id', first it will check whether the same e_id is in the table anywhere or not, if it is not in the table then only it will update the rows with given e_id, else it will not going to update.
So, my upgradation query is below:
update employee
set e_id='0132'
where concat_ws(',',name,ph_no,pay_scale)=concat_ws(',','AMIT','123456','PL-10')
and not exists (select e_id
from employee
group by e_id
having count(*)>=1);
But it is giving the following error:
ERROR 1093 (HY000): You can't specify target table 'employee' for update in FROM clause
I have tried the below query:
update employee set e_id='0132' where
concat_ws(',',name,ph_no,pay_scale)=concat_ws(',','AMIT','123456','PL-10') and
e_id not in
(select e_id from
(select e_id from employee group by e_id having count(*)>=1) as t);
But this also cannot update the table and showing below result:
Query OK, 0 rows affected (0.01 sec)
Rows matched: 0 Changed: 0 Warnings: 0
also tried the below code:
update employee set
employee.e_id='0132' where
employee.e_id not in (select * from
(select f.e_id from
employee f inner join employee b on
b.name=f.name and b.ph_no=f.ph_no and b.pay_scale=f.pay_scale) as tmp)
and employee.name='AMIT' and employee.ph_no='123456' and employee.pay_scale='PL-10';
but this also cannot update the table and gives below result:
Query OK, 0 rows affected (0.00 sec)
Rows matched: 0 Changed: 0 Warnings: 0
Please help. Thank you in advance.
NULL doesn't play the way some people expect with NOT IN: https://dbfiddle.uk/?rdbms=mysql_8.0&fiddle=24c176ff4d4e2c52309aaca14cc121c5 So, just put WHERE e_id IS NOT NULL in the sub-query. Also, HAVING COUNT(*) >= 1 can be removed as it's always going to return a value of 1 or more...
update
employee
set
e_id='0132'
where
name = 'AMIT'
and ph_no = '123456'
and pay_scale = 'PL-10'
and e_id not in (select e_id from
(select distinct e_id
from employee
where e_id IS NOT NULL
)
as t
);
https://dbfiddle.uk/?rdbms=mysql_8.0&fiddle=2a0b036a7d1db9138e3ab29af3d346f8

How to maintain the sort at insert-select scripts?

We have a table called tblINUser, which has many records and occupies a vast amount of space. In an attempt to reduce the amount of used space, we create a table called tblINUserSortByFilter which contains all the possible text values of this field and we create a foreign key in tblINUser that numerically references this value. We have several databases, because this database is sharded, so it would be great to sort the values similarly accross databases. This was the first attempt:
CREATE TABLE MC.tblINUserSortByFilterType(
pkINUserSortByFilterTypeID SMALLINT(6) PRIMARY KEY AUTO_INCREMENT,
SortByFilter varchar(45) COLLATE utf8mb4_unicode_ci NOT NULL DEFAULT 'first',
INDEX(SortByFilter)
);
INSERT INTO MC.tblINUserSortByFilterType(SortByFilter)
SELECT DISTINCT SortByFilter
FROM MC.tblINUser
ORDER BY SortByFilter = 'first';
ALTER TABLE MC.tblINUser
ADD COLUMN fkINUserSortByFilterTypeID SMALLINT(6) DEFAULT 1,
ADD INDEX (fkINUserSortByFilterTypeID);
UPDATE MC.tblINUser INUser
JOIN MC.tblINUserSortByFilterType INUserSortByFilterType
ON INUser.SortByFilter = INUserSortByFilterType.SortByFilter
SET INUser.fkINUserSortByFilterTypeID = INUserSortByFilterType.pkINUserSortByFilterTypeID;
ALTER TABLE MC.tblINUser
DROP COLUMN SortByFilter;
You may argue, correctly that the sort has the only criteria, which is ORDER BY SortByFilter = 'first' and a clause of ORDER BY SortByFilter = 'first', SortByFilter would be an obvious improvement. This would be a correct criticism, yet, even though we may have a chaotic behavior starting from the second record, it would be reasonable to expect that the very first inserted record would be first, yet, unfortunately, this is not the case. Running select * from MC.tblINUserSortByFilterType; yields
+----------------------------+----------------------------+
| pkINUserSortByFilterTypeID | SortByFilter |
+----------------------------+----------------------------+
| 5 | first |
| 4 | first-ASC |
| 3 | last |
| 1 | none |
| 2 | StatTeacher.IsActive DESC |
+----------------------------+----------------------------+
as we can see, not even this expectation is met, since first has an id of 5. An improvement is achieved by changing the inserts to
INSERT INTO MC.tblINUserSortByFilterType(SortByFilter)
SELECT DISTINCT SortByFilter
FROM MC.tblINUser
WHERE SortByFilter = 'first';
INSERT INTO MC.tblINUserSortByFilterType(SortByFilter)
SELECT DISTINCT SortByFilter
FROM MC.tblINUser
WHERE SortByFilter <> 'first';
and then the result of the same selection we get this result:
+----------------------------+----------------------------+
| pkINUserSortByFilterTypeID | SortByFilter |
+----------------------------+----------------------------+
| 1 | first |
| 3 | first-ASC |
| 4 | last |
| 2 | none |
| 5 | StatTeacher.IsActive DESC |
+----------------------------+----------------------------+
5 rows in set (0.00 sec)
as we can see, first is correctly receiving a value of 1. Yet, it seems that if we run the same inserts over different copies of the database, the order of subsequent rows might be unreliable. So, how could we ensure that the records would be inserted in the exact order that the following query yields?
SELECT DISTINCT SortByFilter
FROM MC.tblINUser
WHERE SortByFilter = 'first', SortByFilter;
I know that we can solve this by
using a cursor for the insert
looping the records received
inserting them individually
But that would have as many insert statements as the number of records the above query yields. Is there a way to achieve the same with a single command?
it would be reasonable to expect that the very first inserted record would be first
I don't think so. You used ORDER BY SortByFilter = 'first' which returns 0 for all values except 'first', followed by 1 for 'first'. The value 1 sorts after the value 0, so the entry 'first' ends up being last. The other values end up sorting more or less randomly.
Demo:
mysql> create table mytable (SortByFilter varchar(64));
Query OK, 0 rows affected (0.02 sec)
mysql> insert into mytable values ('first'), ('first-ASC'),
('last'), ('none'), ('StatTeacher.IsActive DESC');
Query OK, 5 rows affected (0.01 sec)
Records: 5 Duplicates: 0 Warnings: 0
mysql> select SortByFilter='first', SortByFilter from mytable
order by SortByFilter = 'first';
+----------------------+---------------------------+
| SortByFilter='first' | SortByFilter |
+----------------------+---------------------------+
| 0 | first-ASC |
| 0 | last |
| 0 | none |
| 0 | StatTeacher.IsActive DESC |
| 1 | first |
+----------------------+---------------------------+
I suggest do not rely on automatic sorting. Be specific about the sort order of every value. Here's one way to do it:
mysql> select field(SortByFilter, 'first', 'first-ASC',
'none', 'StatTeacher.IsActive DESC', 'last') AS SortOrder,
SortByFilter
from mytable order by SortOrder;
+-----------+---------------------------+
| SortOrder | SortByFilter |
+-----------+---------------------------+
| 1 | first |
| 2 | first-ASC |
| 3 | none |
| 4 | StatTeacher.IsActive DESC |
| 5 | last |
+-----------+---------------------------+
To get the rows in a particular order, you must use an ORDER BY. That is straightforward to do if the object of the ORDER BY is a string and you want alphabetical order, or it is numeric and you want it in numeric order. Ditto for the reverse by using DESC.
For for some abnormal ordering, here is one trick:
ORDER BY FIND_IN_SET(my_column, "first,second,third,fourth")
Another:
ORDER BY my_column != 'first', my_column
That will list 'first' first, then do the rest in alphabetic order. (I am assuming my_column is a VARCHAR.)
ORDER BY my_column = 'last', my_column
Note that a boolean expression evaluates to 0 (for false) or 1 (for true); I am then depending on the sort order of 0 and 1.

MySQL auto-increment based on group

The problem is related to autoincrement with mysql. What I'm trying to achieve is to increment an ID value based on the customer number. So basically i insert data sets without any order into a table. Each time a new customer is inserted, i would like the id column to be incremented, but of course kept for every row related to the customer, see the table below. Is there any way to achieve that via sql? I tried my luck with multiple primary keys and also looked into partioning, but was not able to figure it out by myself.
you can use a query like this:
INSERT INTO autoinc (cid,info,customer)
SELECT
COALESCE(max(cid),0) +1
, 'A Customer 1'
, 12345
FROM autoinc
WHERE customer = 12345;
sample
mysql> SELECT * from autoinc;
Empty set (0,00 sec)
mysql> INSERT INTO autoinc (cid,info,customer)
-> SELECT
-> COALESCE(max(cid),0) +1
-> , 'A Customer 1'
-> , 12345
-> FROM autoinc
-> WHERE customer = 12345;
Query OK, 1 row affected (0,00 sec)
Records: 1 Duplicates: 0 Warnings: 0
mysql> SELECT * from autoinc;
+----+------+--------------+----------+
| id | cid | info | customer |
+----+------+--------------+----------+
| 1 | 1 | A Customer 1 | 12345 |
+----+------+--------------+----------+
1 row in set (0,00 sec)
mysql> INSERT INTO autoinc (cid,info,customer)
-> SELECT
-> COALESCE(max(cid),0) +1
-> , 'A Customer 1'
-> , 12345
-> FROM autoinc
-> WHERE customer = 12345;
Query OK, 1 row affected (0,00 sec)
Records: 1 Duplicates: 0 Warnings: 0
mysql> SELECT * from autoinc;
+----+------+--------------+----------+
| id | cid | info | customer |
+----+------+--------------+----------+
| 1 | 1 | A Customer 1 | 12345 |
| 2 | 2 | A Customer 1 | 12345 |
+----+------+--------------+----------+
2 rows in set (0,00 sec)
mysql> INSERT INTO autoinc (cid,info,customer)
-> SELECT
-> COALESCE(max(cid),0) +1
-> , 'B Customer 2'
-> , 9876
-> FROM autoinc
-> WHERE customer = 9876;
Query OK, 1 row affected (0,00 sec)
Records: 1 Duplicates: 0 Warnings: 0
mysql> SELECT * from autoinc;
+----+------+--------------+----------+
| id | cid | info | customer |
+----+------+--------------+----------+
| 1 | 1 | A Customer 1 | 12345 |
| 2 | 2 | A Customer 1 | 12345 |
| 3 | 1 | B Customer 2 | 9876 |
+----+------+--------------+----------+
3 rows in set (0,00 sec)
mysql> INSERT INTO autoinc (cid,info,customer)
-> SELECT
-> COALESCE(max(cid),0) +1
-> , 'A Customer 1'
-> , 12345
-> FROM autoinc
-> WHERE customer = 12345;
Query OK, 1 row affected (0,00 sec)
Records: 1 Duplicates: 0 Warnings: 0
mysql> SELECT * from autoinc;
+----+------+--------------+----------+
| id | cid | info | customer |
+----+------+--------------+----------+
| 1 | 1 | A Customer 1 | 12345 |
| 2 | 2 | A Customer 1 | 12345 |
| 3 | 1 | B Customer 2 | 9876 |
| 4 | 3 | A Customer 1 | 12345 |
+----+------+--------------+----------+
4 rows in set (0,00 sec)
mysql>
What you probably need is to have different values for ID for each customer. The easiest way to achieve this is to use an AUTO_INCREMENT column as PK of your table.
It is an implementation detail that for consecutively inserted rows an AUTO_INCREMENT column has consecutive values. And the previous statement is not even true. It just happens some times, it is not guaranteed. If an INSERT statement is enclosed in a transaction that is rolled back, the value generated by that insert is skipped. Also, if an INSERT statements that use ON DUPLICATE KEYS UPDATE tries to insert many rows but some of them already exist in the table then the IDs generated for the duplicate keys are skipped.
What I want to stress out is that there is no point trying to get consecutive values using an AUTO_INCREMENT column and it is not even possible.
Back to your problem, if the column ID is the PK of the table and its type is INT AUTO_INCREMENT then MySQL guarantees there won't be two rows having the same value in the ID column and this also satisfies your need to have different values for ID for all the rows with the same value in customer.
You could procedurally do this using a stored procedure, which I won't elaborate on (unless requested) as it isn't a simple query (as you're asking for).
A hacky solution would be to bulk insert into a new joining table:
CREATE TABLE auto_inc_customer_id (
id INT UNSIGNED NOT NULL AUTO_INCREMENT,
customer_id INT UNSIGNED NOT NULL, -- Could/should add a FK constraint
PRIMARY KEY (id)
) ENGINE=innodb;
INSERT INTO auto_inc_customer_id SELECT NULL, DISTINCT(Customer) FROM YourExistingTable;
See: http://dev.mysql.com/doc/refman/5.7/en/ansi-diff-select-into-table.html

Auto Increment reset to 0, but cannot insert value with id=0. Does not happen for values >0

I've just stumbled on a very weird behaviour:
Imagine we have a table customers:
MariaDB [connections]> describe customers;
+--------------+-------------+------+-----+---------+----------------+
| Field | Type | Null | Key | Default | Extra |
+--------------+-------------+------+-----+---------+----------------+
| customerId | int(11) | NO | PRI | NULL | auto_increment |
| customerName | varchar(50) | NO | | NULL | |
+--------------+-------------+------+-----+---------+----------------+
2 rows in set (0.00 sec)
Insert a couple of values:
insert into customers(customerName) values('Foo');
insert into customers(customerName) values('Bar');
Then delete everything and reset the auto increment:
DELETE FROM customers;
ALTER TABLE customers AUTO_INCREMENT = 0;
Now, insert a new value with customerId=0:
INSERT INTO customers(customerId,customerName) VALUES(0,'Site owner');
And see the result:
MariaDB [connections]> select * from customers;
+------------+--------------+
| customerId | customerName |
+------------+--------------+
| 1 | Site owner |
+------------+--------------+
1 row in set (0.00 sec)
customerId is set to 1!!!!
Repeat the same procedure but reset to 5 and insert 5, everything is OK:
MariaDB [connections]> delete from customers;
Query OK, 1 row affected (0.00 sec)
MariaDB [connections]> ALTER TABLE customers AUTO_INCREMENT = 5;
Query OK, 0 rows affected (0.00 sec)
Records: 0 Duplicates: 0 Warnings: 0
MariaDB [connections]> INSERT INTO customers(customerId,customerName) VALUES(5,'Site owner');
Query OK, 1 row affected (0.00 sec)
MariaDB [connections]> select * from customers;
+------------+--------------+
| customerId | customerName |
+------------+--------------+
| 5 | Site owner |
+------------+--------------+
1 row in set (0.00 sec)
What is going on here? How can I insert the value '0' with insert values? (Yes, I can edit afterwards but for various reasons it is not practical for my case).
Thanks!
I've referred the answer from the link
You can use:
SET [GLOBAL|SESSION] sql_mode='NO_AUTO_VALUE_ON_ZERO'
Which as described here, will prevent MySQL from interpreting an INSERT/UPDATE ID of 0 as being the next sequence ID. Such behaviour will be limited to NULL.
It is what I'd consider pretty bad behaviour from the application though. You'll have to be real careful that it's used consistently, especially if you choose to implement replication at a later date.
This is impossible.
0 is reserved for auto_increment field. When you insert to auto increment row 0 or null then mysql insert record with current auto increment value.

Set iterative values in rows of a table

I have the following table
id name address empid
1 AA aa 0
2 BB bb 0
3 CC cc 0
I need to write a query to set empid starting from 1. How to write it please. Do i have to use a stored procedure to that or can do it with a normal query?
Thank You.
Here is a way to do it that utilizes a pretty obscure assignment operator in MySQL. This solution won't skip numbers in the case of gaps in the primary key sequence like some of the other solutions.
set #count = 0;
update test set empid = #count := #count+1;
Here is the proof:
mysql> create table test (
-> id int unsigned primary key auto_increment,
-> name varchar(32) not null,
-> address varchar(32) not null,
-> empid int unsigned not null default 0
-> ) engine=innodb;
Query OK, 0 rows affected (0.02 sec)
mysql> insert into test (name, address)
-> values ('AA', 'aa'), ('BB', 'bb'), ('CC', 'cc');
Query OK, 3 rows affected (0.00 sec)
Records: 3 Duplicates: 0 Warnings: 0
mysql> select * from test;
+----+------+---------+-------+
| id | name | address | empid |
+----+------+---------+-------+
| 1 | AA | aa | 0 |
| 2 | BB | bb | 0 |
| 3 | CC | cc | 0 |
+----+------+---------+-------+
3 rows in set (0.00 sec)
mysql> set #count=0;
Query OK, 0 rows affected (0.00 sec)
mysql> update test set empid = #count := #count+1;
Query OK, 3 rows affected (0.00 sec)
Rows matched: 3 Changed: 3 Warnings: 0
mysql> select * from test;
+----+------+---------+-------+
| id | name | address | empid |
+----+------+---------+-------+
| 1 | AA | aa | 1 |
| 2 | BB | bb | 2 |
| 3 | CC | cc | 3 |
+----+------+---------+-------+
3 rows in set (0.00 sec)
If you are looking to put 1 in empid for the first row, 2 for the second, etc. the easiest way would be to use your id field that is already doing this like so:
UPDATE table
SET empid = id
The only thing you need to worry about is missing numbers in the id column. If that would be an issue and you are missing id numbers, you will have to use a different method. To do that, you would need to do something like this:
DECLARE #counter int
SET #counter = 1
UPDATE table
SET #counter = empid = #counter + 1
As #BiggsTRC suggested you can use id to set empid. If not, you can create stored procedure or some PHP code to do that.
If your ID is not "AutoIncrement" field, you can consider a new column as autoincrement field and assign that value to emp with update query and later delete that new column. (These are some alternates, you need to choose the best one)
UPDATE `test` SET `empid`=`id`
But why would you want to do it? It's pretty much definition of redundancy.