溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊(cè)×
其他方式登錄
點(diǎn)擊 登錄注冊(cè) 即表示同意《億速云用戶服務(wù)條款》

怎么使用mysql5.6解析JSON字符串

發(fā)布時(shí)間:2022-07-06 14:19:22 來源:億速云 閱讀:1027 作者:iii 欄目:開發(fā)技術(shù)

本篇內(nèi)容主要講解“怎么使用mysql5.6解析JSON字符串”,感興趣的朋友不妨來看看。本文介紹的方法操作簡(jiǎn)單快捷,實(shí)用性強(qiáng)。下面就讓小編來帶大家學(xué)習(xí)“怎么使用mysql5.6解析JSON字符串”吧!

mysql5.6 解析JSON字符串

支持復(fù)雜的嵌套格式

廢話不多說,先上代碼。

CREATE FUNCTION `json_parse`(`jsondata` longtext,`keyname` text) RETURNS text CHARSET utf8
BEGIN
	DECLARE delim VARCHAR(128);
	DECLARE	result longtext;
	DECLARE startpos INTEGER;
	DECLARE endpos INTEGER;
	DECLARE endpos1 INTEGER;
  DECLARE findpos INTEGER;
	DECLARE leftbrace INTEGER;
	DECLARE tmp longtext;
  DECLARE tmp2 longtext;
	DECLARE Flag INTEGER;
 
	SET delim = CONCAT('"', keyname, '": "');
	SET startpos = locate(delim,jsondata);
 
	IF startpos > 0 THEN
		SET findpos = startpos+length(delim);
		SET leftbrace = 1;
		SET endpos = 0;
		SET Flag =1;
		get_token_loop: repeat 
				IF substr(jsondata,findpos,2)='\\"' THEN
					SET findpos = findpos + 2;
					iterate get_token_loop;
				ELSEIF substr(jsondata,findpos,2)='\\\\' THEN
					SET findpos = findpos + 2;
					iterate get_token_loop;
				ELSEIF substr(jsondata,findpos,1)='"' AND Flag = 1  THEN 
						SET endpos = findpos;
						SET findpos = LENGTH(jsondata)+1;
						leave get_token_loop;
				END IF;
				SET findpos = findpos + 1;
			UNTIL findpos > LENGTH(jsondata) END repeat;
			
			IF endpos > 0 THEN
				SELECT 
					substr(
						jsondata
						,startpos
						+length(delim)#取出value值的起始位置
						,endpos#取出value值的結(jié)束位置
						-(
							startpos
							+length(delim)
							)#減去value值的起始位置,得到value值字符長(zhǎng)度
					) INTO result
				FROM DUAL;
				SET result= replace(result,'\\"','"');
				SET result= replace(result,'\\\\','\\');
			ELSE 
				SET result=null;
			END IF;
				/*
		SELECT 
			substr(
				jsondata
				,locate(delim,jsondata)
				+length(delim)#取出value值的起始位置
				,locate(
					'"'
					,jsondata
					,locate(delim,jsondata)
					+length(delim)
					)#取出value值的結(jié)束位置
				-(
					locate(delim,jsondata)
					+length(delim)
					)#減去value值的起始位置,得到value值字符長(zhǎng)度
			) INTO result
		FROM DUAL;	*/
	ELSE
			SET delim = CONCAT('"', keyname, '": {');
			SET startpos = locate(delim,jsondata);
			IF startpos > 0 THEN
				SET findpos = startpos+length(delim);
				SET leftbrace = 0;
				SET endpos = 0;
				SET Flag =0;
	
			get_token_loop: repeat 
					IF substr(jsondata,findpos,2)='{"' THEN
						SET leftbrace = leftbrace + 1;
						SET findpos = findpos + 2;
						iterate get_token_loop;
					ELSEIF substr(jsondata,findpos,2)='\\"' THEN
						SET findpos = findpos + 2;
						iterate get_token_loop;
					ELSEIF substr(jsondata,findpos,3)=': "' THEN
							SET Flag = 1;
							SET findpos = findpos + 3;
							iterate get_token_loop;
					ELSEIF substr(jsondata,findpos,1)='"' THEN
						SET Flag = 0;
					ELSEIF substr(jsondata,findpos,1)='}' AND Flag = 0  THEN
						IF leftbrace > 0 THEN
							SET leftbrace = leftbrace - 1;
						ELSE 
							SET endpos = findpos;
							SET findpos = LENGTH(jsondata)+1;
						END IF;
					END IF;
					SET findpos = findpos + 1;
				UNTIL findpos > LENGTH(jsondata) END repeat;
				
				IF endpos > 0 THEN
					SELECT 
						substr(
							jsondata
							,startpos
							+length(delim)#取出value值的起始位置
							,endpos#取出value值的結(jié)束位置
							-(
								startpos
								+length(delim)
								)#減去value值的起始位置,得到value值字符長(zhǎng)度
						) INTO result
					FROM DUAL;
					SET result=CONCAT("{",result, '}');
				ELSE 
					SET result=null;
				END IF;
			ELSE 
				SET delim = CONCAT('"', keyname, '": [');
				SET startpos = locate(delim,jsondata);
				IF startpos > 0 THEN
					SET findpos = startpos+length(delim);
					SET leftbrace = 0;
					SET endpos = 0;
 
						SET tmp = substring_index(jsondata,delim,-1);
						SET tmp2 = substring_index(tmp,']',1);
						
				   IF locate('[',tmp2) =0 THEN					
							SET endpos = locate(']',tmp);
							SET endpos = endpos+findpos-1;
					 ELSE
							get_token_loop: repeat 
									IF substr(jsondata,findpos,2)='\\"' THEN
										SET findpos = findpos + 2;
										iterate get_token_loop;
									ELSEIF substr(jsondata,findpos,3)=': "' THEN
											SET Flag = 1;
											SET findpos = findpos + 3;
											iterate get_token_loop;
									ELSEIF substr(jsondata,findpos,1)='[' AND Flag = 0 THEN
										SET leftbrace = leftbrace + 1;
										SET findpos = findpos + 1;
										iterate get_token_loop;
									ELSEIF substr(jsondata,findpos,1)='"' THEN
										SET Flag = 0;
									ELSEIF substr(jsondata,findpos,1)=']' AND Flag = 0  THEN
										IF leftbrace > 0 THEN
											SET leftbrace = leftbrace - 1;
										ELSE 
											SET endpos = findpos;
											SET findpos = LENGTH(jsondata)+1;
										END IF;
									END IF;
									SET findpos = findpos + 1;
								UNTIL findpos > LENGTH(jsondata) END repeat;
					END IF;
					IF endpos > 0 THEN
						SELECT 
							substr(
								jsondata
								,startpos
								+length(delim)#取出value值的起始位置
								,endpos#取出value值的結(jié)束位置
								-(
									locate(delim,jsondata)
									+length(delim)
									)#減去value值的起始位置,得到value值字符長(zhǎng)度
							) INTO result
						FROM DUAL;
						SET result=CONCAT("[",result, ']');
					ELSE 
						SET result=null;
					END IF;
				ELSE 					
					SET delim = CONCAT('"', keyname, '": ');
					SET startpos = locate(delim,jsondata);
					IF startpos > 0 THEN
						SET endpos = locate(',',jsondata,startpos+length(delim));
						SET endpos1 = locate('}',jsondata,startpos+length(delim));
						IF endpos>0 OR endpos1>0 THEN
								IF endpos1>0 AND endpos1 < endpos OR endpos =0 THEN
									SET endpos = endpos1;
								END IF;
								SELECT 
									substr(
										jsondata
										,startpos
										+length(delim)#取出value值的起始位置
										,endpos#取出value值的結(jié)束位置
										-(
											locate(delim,jsondata)
											+length(delim)
											)#減去value值的起始位置,得到value值字符長(zhǎng)度
									) INTO result
								FROM DUAL;
								
								IF STRCMP(result,'null')=0 THEN
									SET result=null;
								END IF;
						ELSE 					
							SET result=null;
						END IF;
					ELSE 					
						SET result=null;
					END IF;
				END IF;
			END IF;
	END IF;
	if result='' and RIGHT(keyname,2)='Id' then
		SET result=null;
	end if;
	RETURN result;
END

jsondata需要嚴(yán)格的json格式(注意逗號(hào)和分號(hào)以及雙引號(hào)之間的空格)

SET jsondata='{"CurrentPage": 1, "data": [{"config": "123"}, {"config": "456"}], "PageSize": 10}' 
SELECT json_parse(jsondata, 'CurrentPage') INTO CurrentPage;
SELECT json_parse(jsondata, 'data') INTO data;

這邊如果想獲取config的內(nèi)容,可以這樣處理

        SET count = (LENGTH(data)-LENGTH(REPLACE(data,'},','')))/2+1;
        SET i = 0;
        WHILE i < count DO
            SET SetObject = SUBSTRING_INDEX(SUBSTRING_INDEX(data,'},',i+1),'},',-1);
            IF LENGTH(SetObject)>0 THEN
                SELECT json_parse(SetObject, 'config') INTO config;    
            END IF;
            SET i = i + 1;
        END WHILE;

不足之處,jsondata數(shù)據(jù)多的情況下,會(huì)有效率問題。

mysql5.6及以下解析json方法

之前在公司發(fā)現(xiàn)在線的查詢平臺(tái)是MySQL5.6,不能用JSON_EXTRACT,也不能用存儲(chǔ)過程,所以只能自己編了一個(gè)簡(jiǎn)單的小查詢,幾條數(shù)據(jù)還是能查的,如果數(shù)據(jù)量大的話,估計(jì)耗的資源就會(huì)比較多。

先說一下問題的背景

是想在'{"platform":"Android","source":"tt","details":null}'這一串東西里面找到source這個(gè)key對(duì)應(yīng)的value值。

這個(gè)方法是先找到source":"這個(gè)字符串的起始位置和長(zhǎng)度,這樣就能夠找到value值的起始位置;再找到這個(gè)字符串以后第一個(gè)"出現(xiàn)的位置,就能得到value值的結(jié)束位置。

再利用substr函數(shù),就可以取出對(duì)應(yīng)的位置。

下面是對(duì)應(yīng)的代碼 

SELECT 
'{"platform":"Android","source":"tt","details":null}' as 'sample'
,substr(
  '{"platform":"Android","source":"tt","details":null}'
  ,locate('source":"','{"platform":"Android","source":"tt","details":null}')
   +length('source":"')#取出value值的起始位置
  ,locate(
  		'"'
  		,'{"platform":"Android","source":"tt","details":null}'
  		,locate('source":"','{"platform":"Android","source":"tt","details":null}')
  		+length('source":"')
  		)#取出value值的結(jié)束位置
	  -(
	  	locate('source":"','{"platform":"Android","source":"tt","details":null}')
	  	+length('source":"')
	  	)#減去value值的起始位置,得到value值字符長(zhǎng)度
  ) as result
FROM DUAL

運(yùn)行以后,就得到result的結(jié)果,就是tt。如果需要其他元素,就替換一下對(duì)應(yīng)的key值和字段,就好了。

到此,相信大家對(duì)“怎么使用mysql5.6解析JSON字符串”有了更深的了解,不妨來實(shí)際操作一番吧!這里是億速云網(wǎng)站,更多相關(guān)內(nèi)容可以進(jìn)入相關(guān)頻道進(jìn)行查詢,關(guān)注我們,繼續(xù)學(xué)習(xí)!

向AI問一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI