I have a database of customer information. There are separate rows for billing address and shipping address with a flag signifying which it is; BA, SA. Many of the records are set to BA therefore I have duplicates for each customer. I need to set a duplicate record to SA.
I tried this but it updated ALL the records that were duplicate. Instead I want to update only one of the duplicate records;
UPDATE customer1 AS C1 JOIN
(
SELECT Ca.user_id, C2.CID, Ca.address_type FROM
customer1 AS Ca JOIN
customer2 AS C2 ON CC.user_id = C2.CID
GROUP BY Ca.user_id
HAVING COUNT(*) > 1
) AS C2a ON
C1.user_id = C2.CID
SET C1.address_type = 'SA'
...
LIMIT 0,1
Note that as others have said, you should never have duplicate rows in your database in the first place - it implies your schema is wrong. Also, you'll get a warning using LIMIT without an ORDER BY
As far as the data base is concerned, duplicate records are indistiguishable.
I think your best option is to add an automatically generated ID (see auto_increment) to each record. Then you can uniquely identify the record you want to update.
The other alternative is to copy the data from one of the duplicates, delete them, insert one record then insert the other with the required change.
You should normalize your table schemas to avoid dupplicate data.
Meaning, I would suggest an "address" table with all the adresses
and extend the "customer" table by a field BA_address and SA_address, pointing to these addresses.
If you now need to "duplicate" a record from BA to SA, you just put the same addressID inside the SA field, like in the BA field.
Related
I have two tables. The first is named master_list. It has these fields: master_id, item_id, name, img, item_code, and length. My second table is named types_join. It has these fields: master_id and type_id. (There is a third table, but it is not being used in the queries. It is more for reference.) I need to be able to combine these two tables so that I can sift the results to only show certain ones but part of the information to sift is on one table and the other part is on the other one. I don't want duplicate answers.
For example say I only want items that have a type_id of 3 and a length of 18.
When I use
SELECT * FROM master_list LEFT JOIN types_join ON master_list.master_id=types_join.master_id WHERE types_join.type_id = 3 AND master_list.length = 18"
it finds the same thing twice.
How can I query this so I won't get duplicate answers?
Here are the samples from my tables and the result I am getting.
This is what I get with an INNER JOIN:
BTW, master_id and name both only have unique information on the master_list table. However, the types_join table does use the master_id multiple times later on, but not for Lye. That is why I know it is duplicating information.
If you want unique rows from master_list, use exists:
SELECT ml.*
FROM master_list ml
WHERE ml.length = 18 AND
EXISTS (SELECT 1
FROM types_join tj
WHERE ml.master_id = tj.master_id AND tj.type_id = 3
);
Any duplicates you get will be duplicates in master_list. If you want to remove them, you need to provide more information -- I would recommend a new question.
Thank you for the data. But as you can see enter link description here, there is nothing wrong with your query.
Have you tried create an unique index over master_id, just to make sure that you do not have duplicated rows?
CREATE UNIQUE INDEX MyMasterUnique
ON master_list(master_id);
I have a table full of data in "businesses", and a new table called "table 9" which has come in through an import. I'm trying to migrate the table 9 data into businesses but i need to make sure it doesn't already exist. I have no choice but to run this live (i have a backup)
This is my code so far :
INSERT INTO businesses
(Business, Address1,Address2,Address3,Town,Postcode,BusinessType,Contact,Position,Telephone)
SELECT Company,
line1,
line2,
line3,
town,
postcode,
trade,
(SELECT CONCAT(`ContactSalutation`, ' ', `ContactFirstName`, ' ', `ContactLastName`) FROM telesales.`table 9`),
ContactPosition,
phoneno pnum
FROM telesales.`table 9` ts
where pnum NOT IN (SELECT DISTINCT Telephone
FROM businesses
WHERE Telephone = pnum)
Firstly is this going to do what i expect? only insert if the phone number in table 9 doesnt exist in businesses table, and is there a way to say if it does exist then update it instead with the new data?
Firstly,
(SELECT CONCAT(`ContactSalutation`, ' ', `ContactFirstName`, ' ', `ContactLastName`) FROM telesales.`table 9`),
is almost certainly not what you want. You're saying "get all this information from table 9 and put it into businesses", without a join or a where clause. Not sure how MySQL reacts to this, but the best case is that you get a random row, not the row associated with the one you're inserting. I think you want to replace it with:
CONCAT(`ContactSalutation`, ' ', `ContactFirstName`, ' ', `ContactLastName`),
Secondly, this query is highly dependent on the formatting of phone numbers. That's probably not a good idea, unless you can guarantee that formatting is consistent.
For instance is "00 31 20 787 9000" the same phone number as "00 31 207 87 9000"?
In cases like this, I typically create an additional column on table9 (e.g. "businessID"), and write queries to populate that.
For instance:
update table9 t9
inner join businesses b
on b.phone = t9.phone
set businessID = b.businessID
Sense check the table; you may find you then need to do
update table9 t9
inner join businesses b
on b.phone = trim(t9.phone)
set businessID = b.businessID
Finally, you can insert the records from table9 into businesses that have a null businessID, and update the others.
if "if it exists" means, it has the same primary key, then yes, you should use REPLACE instead of INSERT. See http://dev.mysql.com/doc/refman/5.5/en/replace.html
However, you should probably create a copy of your target table first ;o)
REPLACE does work but ..
REPLACE works exactly like INSERT, except that if an old row in the
table has the same value as a new row for a PRIMARY KEY or a UNIQUE
index, the old row is deleted before the new row is inserted.
But that means a great deal more of time and effort will be spent by the database on updating the indexes. Better would be to use INSERT IGNORE or INSERT .. ON DUPLICATE KEY
Imagine an 1:N relationship among tables t_parent and t_child. The PK of the parent table t_parent is requestid and of course this is the FK for t_child. Also, t_child has another field called usermail which contains en email address. I want to write a SELECT statement which will return for every record of t_parent:
1)requestid (easy)
2)the number of records in t_child assosiated with the corresponding requestid (by using count, I am getting only one row as output even if the records of t_parent are more)
3)the emails from field usermail of the associated (with current requestid) records of t_child, all together combined in a string.
Is the above SELECT possible?
Thank you
SELECT t_parent.id, COUNT(*), GROUP_CONCAT(t_child.usermail)
FROM t_parent
LEFT JOIN t_child
ON t_parent.id = t_child.parent_id
GROUP BY t_parent.id
Update 4/25/13 6:25AM: I am using MyISAM
I have searched a lot and am not sure the best way to do this. I have two tables that have matching values in different columns and need to return all that apply to where clause.
Table 1 name agent
Relevant Column Names agent_name and team
Table 2 name poll_data
Relevant Column Names agent and duid
So I want to count how many poll results I get from each teambut I need to somehow add the team from agent table to poll_data by matching the agent.agent_name to poll_data.name so I can return only data for that team. How can I match the records and then search them in a single query.
try this ...
$query1="SELECT COUNT(*) FROM poll_data JOIN agent ON (poll_data.agent = agent.agent_name) GROUP BY agent.team";
you should normalize the database using foreign key.
My question is similar (but at the same time completely different) than this question:
Contacts Database
The question is simple: How can I create a Contacts database table which stores a user id and contact id without duplicating keys.
For example, if I have a table called Contacts, it would have a column user_id, and a column contact_id.
Once I do that, it should be as simple as inserting the user and the added contact. Once that is done though, how do I select all of a user's contacts? Also, how do I narrow down the contact entry enough to delete it if need be?
I ended up just creating a table with two foreign keys and then selecting them based on either of the fields.
For example (pseudo code--no specific language, just english):
Table Contact:
user = ForeignKey(from user table)
contact = ForeignKey(from user table)
Then whenever I need something from them, I'll check if the user field contains what I want and then I'll check if the contact field has what I want. This way I don't have to repeat records and I can still find what I need.
Thanks for your answers.
Similar to the question in the link. You would have 3 tables.
Table 1
User_ID
Name
PK(User_ID)
Table 2
Contact_id
Address
Phone_Number
etc...
PK(Contact_id)
Table 3
User_ID
Contact_id
PK(User_ID, Contact_id)
Here you would have ContactID in table 2 as an autoinc column.
Also, when inserting in Table 3, MySQL would throw an error if there is a duplicate.
To select all of a users contacts, use:
SELECT *
FROM Table_2 join Table_3
ON Table_2.Contact_id = Table_3.contact_id
WHERE Table2.User_id = <userid>
Or if you need it for a particular name, then
SELECT *
FROM Table_1 JOIN Table_2
ON Table_1.User_id = Table_2.User_id
JOIN Table_3
ON Table_2.Contact_id = Table_3.contact_id
WHERE Table1.name = <user name>
there are two questions.
" how do I select all of a user's contacts?"
So you have a table tbl_contacts(user_id, contact_id) both them are your primary key, so you won't get duplicated data.
I you want to list all contacts for user_id = ?
SELECT *
FROM tbl_contacts
WHERE user_id = ?
You might want to clarify your second question "Also, how do I narrow down the contact entry enough to delete it if need be?"
You probably have some other properties belong to the user's contact and you will need to use those properties to search for.(eg.: contact_name or contact_number) and when you have 1 record as a result of a query you can -> DELETE FROM tbl_contact WHERE contact_id = ?
If this is not the answer you wanted please clarify your question.