MySQL sorgusundaki metni sayıya dönüştürme


138

MySQL sorgusunda metni sayıya dönüştürmek mümkün mü? Bir ad ve "ad-sayı" biçiminde bir sayı içeren bir tanımlayıcı ile bir sütun var. Sütun VARCHAR tipindedir. Satırları sayıya göre sıralamak istiyorum (aynı ada sahip satırlar), ancak sütun karakter sırasına göre sıralanır, yani

name-1
name-11
name-12
name-2

Numarayı kesersem, 'varchar' numarasını 'gerçek' sayıya dönüştürebilir ve satırları sıralamak için kullanabilir miyim? Aşağıdaki siparişi almak istiyorum.

name-1
name-2
name-11
name-12

Numarayı ayrı bir sütun olarak gösteremiyorum.

düzenlendi 2011-05-11 9:32

Aşağıdaki çözümü buldum ... ORDER BY column * 1. İsim herhangi bir sayı içermeyecekse, bu çözümü kullanmak için kaydediliyor mu?


1
name tam olarak name veya herhangi bir karakter olabilir? Yani: dört karakter uzunluğunda bir dize mi, yoksa gerçek bir isim mi?
Marco

nameherhangi bir harf dizisi olabilir.
çek

Yanıtlar:


256

Bu çalışmalı:

SELECT field,CONVERT(SUBSTRING_INDEX(field,'-',-1),UNSIGNED INTEGER) AS num
FROM table
ORDER BY num;

1
Belgelere bir açıklama ve bağlantı ekleyebilir misiniz?
Angelo Fuchs

Dizem "name-abc12" gibidir. Kodunuzu ekleyerek, yalnızca "-" işaretinden sonraki ilk karakterler bir harfle başlamazsa çalışır. @Marco Bana nerede koşul olmadan harfleri görmezden gelmenin bir yolunu söyleyebilir misiniz?
Eduardo

1
@Eduardo benim sorgu "-" sonra dize almak ve bir sayıya dönüştürmek gerekiyordu (bir sayı olmalıdır). Senin durumunda muhtemelen düzenli bir ifade kullanmaya devam edecektim ...
Marco

@Marco düzenli ifade yaptı, bahşiş için teşekkür ederim.
Eduardo

32

Sen kullanabilirsiniz SUBSTRINGve CONVERT:

SELECT stuff
FROM table
WHERE conditions
ORDER BY CONVERT(SUBSTRING(name_column, 6), SIGNED INTEGER);

name_column"Name-" değerlerine sahip sütun nerede . SUBSTRINGKaldırır altıncı karakterden önce her şey (yani "adı-" öneki) ve daha sonra CONVERTdönüştürür gerçek tamsayıya üzerine bıraktı.

GÜNCELLEME : Yorumlardaki değişen koşullar göz önüne alındığında (yani önek herhangi bir şey olabilir), LOCATEkarışıma bir atmanız gerekir :

ORDER BY CONVERT(SUBSTRING(name_column, LOCATE('-', name_column) + 1), SIGNED INTEGER);

Bu, elbette, sayısal olmayan ön ekin içinde tire işareti bulunmadığını varsayar, ancak ilgili yorum şunları söyler:

name herhangi bir harf dizisi olabilir

bu güvenli bir varsayım olmalıdır.


Yorumumu cevaplayarak, bize isim herhangi bir karakter dizisi olabileceğini söyledi , bu yüzden kullanabileceğinizden emin değilim SUBSTRING(name_column, 6). Biliyorum, bunu bize söylemediğinde sen de gönderdin ...
Marco

@Marco: Uyarı için teşekkürler, öneklerle ilgili yeni bilgileri dikkate alması gereken bir güncelleme ekledim. Ama evet, SUBSTRING_INDEX'iniz daha güzel.
mu

23

Sadece CAST kullanın,

CAST(column_name AS UNSIGNED)

Yayın sonucunun türü aşağıdaki değerlerden biri olabilir:

BINARY[(N)]
CHAR[(N)]
DATE
DATETIME
DECIMAL[(M[,D])]
SIGNED [INTEGER]
TIME
UNSIGNED [INTEGER]

14

Dizeden int 'e dönüştürmek için CAST () kullanabilirsiniz . ÖrneğinSELECT CAST('123' AS INTEGER);


15
Bu sürüm belirli mi? Kullanmam SELECT CAST('123' AS SIGNED INTEGER);veya kullanmam lazım SELECT CAST('123' AS UNSIGNED INTEGER);.
Hobo

10
SELECT *, CAST(SUBSTRING_INDEX(field, '-', -1) AS UNSIGNED) as num FROM tableName ORDER BY num;

1
ORDER BY işlevinin numaranızı CONVERT kullanmadan sayı olarak kullandığından emin misiniz? Emin değilim, ama olabilir .. Sadece kendime soruyorum :)
Marco

4

basit bir yol SEÇ '123' + 0


Her ne kadar bu kod sorunu çözmek için yardımcı olsa da , soruyu neden ve / veya nasıl cevapladığı konusunda ek bağlam sağlamak uzun vadeli değerini önemli ölçüde artıracaktır. Lütfen biraz açıklama eklemek için cevabınızı düzenleyin .
Toby Speight

Bu soruya cevap vermedi ama aradığım cevap buydu.
Sagar Shah

çözümünüz en şık ve pratiktir - maalesef soru bağlamında verilen örnek için belirli bir ifade vermediniz - lütfen spesifik olarak değiştirin.
chukko


2

birincil anahtarınız

ABC / EFG / EE / 13/123 (sıra numarası) gibi bir formatta bir dize ise,
bu tür bir dize ayırıcı ("/") ile sıralama için kolayca kullanılabilir

bu tür anahtarlara sahip bir tablo sipariş etmek için aşağıdaki sorguyu kullanabiliriz

SELECT * FROM `TABLE_NAME` ORDER BY 
CONVERT(REVERSE(SUBSTRING(REVERSE(`key_column_name`), 1, LOCATE('/', REVERSE(`key_column_name`)) - 1)) , UNSIGNED INTEGER) DESC


-5

Bunu yapmanın genel bir yolu:

SELECT * FROM your_table ORDER BY LENTH(your_column) ASC, your_column ASC
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.