MySQL-da find_in_set (value, set) uchun sqlite ning teng funksiyasi nima?

Quyidagi misol MySQL-ga tegishli. Masalan, test1 quyidagicha

+----+------------------------+
| id | name                   |
+----+------------------------+
|  2 | 1,2                    |
| 33 | 2,44,33,5              |
|  1 | 11,4,55                |
| 12 | 11,111,122,551,112,221 |
+----+------------------------+

tanlash * test1 dan olishingiz mumkin qaerda find_in_set ('122', name)

u quyidagilarni oladi:

+----+------------------------+
| id | name                   |
+----+------------------------+
| 12 | 11,111,122,551,112,221 |
+----+------------------------+

Sql Lite-da, quyidagi kabi foydalanish mumkin:

select * 
from `test1` 
where name like '%,122,%'
or name like '122,%'
or name like '%,122'
or name = '122'

Masala:

My value is 551,122. In this case,as value is returned from appln we can split the value column & write the query as

(',' || column_name || ',') LIKE '%,551,%' or
(',' || column_name || ',') LIKE '%,122,%'

Buning uchun eng yaxshi g'oya bormi?

Men kabi bo'lishdan qochmoqchiman. Xo'sh, boshqa biron-bir fikr bormi?

0
O'zingizning sxemani o'zgartirmagan holda, nima qilishni xohlasangiz, sof SQLite da bajarilishi mumkin. Uchinchi tomon SQLite eklentlari bo'lishi mumkin, ular siz xohlagan narsani bir qator ma'lumotlar turi bilan bajarishi mumkin yoki siz xohlagan narsani bajarish uchun o'zingizning vazifangizni yozishingiz mumkin.
qo'shib qo'ydi muallif Flimzy, manba
@muistooshort: Ha, albatta? Men qasam ichib aytamanki, men bu yerga murojaat qilgandim ... ehtimol, qo'shimchalarmi? Yoki buni orzu qilardim.
qo'shib qo'ydi muallif Flimzy, manba
@Flimzy: SQLite arrays ni qo'llab-quvvatlamaydi.
qo'shib qo'ydi muallif mu is too short, manba
Kimki find_in_set ni MySQL-ga qo'shgan bo'lsa, unda kimdir gaplashishi kerak.
qo'shib qo'ydi muallif mu is too short, manba
LIKE dan foydalanishingiz mumkin: stackoverflow.com/questions/6979813/…
qo'shib qo'ydi muallif John Weldon, manba
Fikringizni tushunmayapmanmi?
qo'shib qo'ydi muallif John Weldon, manba
"Ism" ma'lumotlar turi mag'lubiyatdir. @John afsus. Men kabi bo'lishdan qochmoqchiman, lekin yaxshiroq echim yo'q bo'lsa, men unga boraman.
qo'shib qo'ydi muallif Angelin Nadar, manba
Ick stackoverflow.com/questions/6979813/... hal qilish uchun indeksni talab qilmayman
qo'shib qo'ydi muallif Angelin Nadar, manba
Mening qiymatim 551,122 emas, balki boshqa unutilgan ishning echimini hal qila olmayman. Buni qanday qilamiz? Biz 122 ta va 551 ta alohida-alohida qilib, ajratishimiz va ajratishimiz mumkin
qo'shib qo'ydi muallif Angelin Nadar, manba

3 javoblar

Mening birinchi fikrim siz CSV ma'lumotlarini relatsion ma'lumotlar bazasidagi ustunga saqlamasligingizdir, alohida birlashma jadvalidan foydalanishingiz kerak.

LIKE bilan bu ishni bajarishingiz mumkin. Sizning sharhingiz uch holatni ko'rganligingizni ko'rsatadi, lekin aslida to'rtta:

select *
from test1
where name like '122,%'
   or name like '%,122'
   or name like '%,122,%'
   or name    = '122'     /* You forgot about this degenerate case */

Indeks oxirgi ish uchun va ehtimol birinchi uchun ishlatilishi mumkin, ammo o'rtadagi ikkita jadvalni skanerlash mumkin. Ma'lumotlaringizni har doim etakchi va orqadan vergulga ega bo'lishga majbur qilsangiz, so'rovni soddalashtirishingiz mumkin:

+----+--------------------------+
| id | name                     |
+----+--------------------------+
|  2 | ,1,2,                    |
| 33 | ,2,44,33,5,              |
|  1 | ,11,4,55,                |
| 12 | ,11,111,122,551,112,221, |
+----+--------------------------+

Keyin birgina LIKE (indeksni ishlatmaydi) dan foydalanishingiz mumkin:

select *
from test1
where name like '%,122,%'

Lekin, albatta, siz qaerda <122 => dan foydalanishingiz va qolganlar uchun boshqa jadvallarga qo'shilishingiz uchun birlashma jadvalidan foydalanishingiz kerak.

4
qo'shib qo'ydi
Siz ham CSV ustunini "nom" deb nomlamasligingiz kerak ... Agar biror kishi/nimani nomi aslida "1,2" bo'lmasa. Ehtimol, bu Star Trek-dan kibernetik yaratuvchilarning ma'lumotlar bazasi.
qo'shib qo'ydi muallif Flimzy, manba
+1 CSV ma'lumotlarini ilişkisel ma'lumotlar bazasida joylashgan ustunga saqlamaslik kerak, nima uchun CSV sifatida saqlab, jadvaldagi bo'sh joyni saqlashni xohlaysiz?
qo'shib qo'ydi muallif Deeptechtons, manba
@ Angelin: Bu qiziqarli yondashuv, lekin siz hali ham sxemani tuzatib, muloqot jadvalidan foydalanishingiz kerak.
qo'shib qo'ydi muallif mu is too short, manba
@Angelin: Ma'lumotlarni birlashma jadvaliga nusxa ko'chirish va uning o'rniga foydalana olmaysizmi?
qo'shib qo'ydi muallif mu is too short, manba
@mu juda qisqa Agar sizning ma'lumotlaringizni har doim etakchi va tomoshabinli vergullarga ega bo'lishga majbur qilsangiz, Jon Veldon bilan bog'lanishingiz mumkin (',' | 'column_name ||', ') Like'%, value,% ' unutilgan ish uchun emas, balki ushbu echim bilan ishlov berilgan
qo'shib qo'ydi muallif Angelin Nadar, manba
@mu juda qisqa: yoki sxemani uchinchi shaxslar bazasi deb hisoblay olmayman
qo'shib qo'ydi muallif Angelin Nadar, manba
OK, uni sinab ko'rishga imkon beradi, ammo uni eng avvalo ustunlik sifatida ko'rib chiqish mumkin, yoki uni moslashtiradigan string funktsiyalarini izlash yoki MySQL-da topish uchun find_in_set
qo'shib qo'ydi muallif Angelin Nadar, manba

Men John Weldonning taktikasi bilan borishni afzal ko'raman,

Shunday qilib,

select *
from test1
where (',' || column_name || ',') LIKE '%,122,%' //any value 

Arizalar

0
qo'shib qo'ydi

Funktsiyani yaratish

public class ConnectionOpenHandler extends Interceptor{
  private static final long serialVersionUID=1;
  private String nameConnection;
  private String jdbcUrl;

  public void handler(Handler handler) throws Exception{
    Context context=(Context)handler.getProperty("context");
    SessionContext sessionContext=(SessionContext)context;

    Class.forName("org.sqlite.JDBC");
    Connection connection=DriverManager.getConnection(jdbcUrl);
    connection.setAutoCommit(false);
    handler.setProperty(nameConnection,connection);
    sessionContext.getProtectedContext().setProperty(nameConnection,connection);

    Function.create(connection,"find_in_set",new FindInSet());
  }
  private class FindInSet extends Function{
    protected void xFunc() throws SQLException{
      String row=this.value_text(0);
      String values=this.value_text(1);

      if(values==null){
        result(0);
        return;
      }

      boolean ok=Arrays.asList(values.split("\\,")).contains(row);
      result(ok?1:0);
    }
  }
}
0
qo'shib qo'ydi