狀態機器的應用:幾十ms在百萬資料量中搜尋

來源:互聯網
上載者:User

      由於一直在學習狀態機器,其知識量之大,確實是我所想象不出來的,最近在論壇裡看問題,只要是能和狀態機器相關的,我都會仔細的捉摸。其中要想學會狀態機器,對記憶體的把握,對資料管理的把握,尤其是對資料結構的把握都是相當基本的要求。說來慚愧,學了這麼長時間。還是不得其門而入,雖然寫了一些程式,總結了一些東西,但是總是和自己所希望的相去甚遠。但是進步總是在潛移默化當中發生的,只要肯好好努力,收穫還是有的。習慣了定一個目標,做一個計劃,之後努力去實現它,但這次真的感覺有點累。為了那遙不可及的目標,還是需要默默的走下去!狀態機器我真愛死你了,欲罷不能。

      呵呵扯遠了,還是言歸正傳吧,昨天早上在論壇裡看到了一個文章

     http://topic.csdn.net/u/20090920/21/8997ec64-c81d-426f-a714-575f3db06b9d.html

     大致要求如下:

     (1).存在資料列表,格式為,每一行為一個對象

             x,y,width,height,zorder

              0,0,10,20,1

               2,2,30,20,2

                ...

                ...

              (x,y,width,height)確定一個正方形,zOrder層次

       (2).要求給定1點(x,y),找出包含該點的所有對象.並按zOrder大小從大向小排

       (3).要求給出一個正方形(x,y,width,height),找出包含該正方形內的所有對象

           (分兩種情況1.完全包含.2不完全包含(只要一部分在方向內就行))

        (4)自已定義資料結構和存放形式,要求演算法複雜度儘可能小,不要給一個要求全部遍曆判斷的方式.

                      最好在O(1)或O(log2n),因為方法調用頻度高和N很大(100000)

總結一下吧,最開始我的方法10萬的資料,我最開始的搜尋方法需要600多個ms,到後來的百萬資料只需要幾十個ms的時間,所有我用到的東西,除了演算法,幾乎都是我最近學習狀態機器練出來的。其中第一個方法從面對問題,到想方法,到編碼,最後到測試,我只花了不到三個小時的時間,我個人對這個結果是很滿意的,雖然我感覺自己的進步很慢。我建議大家多學習學習狀態機器,開闊一下視野(當然或許許你已經不需要了),最起碼要知道,不是編譯原理包含狀態機器,而是狀態機器包含編譯原理,詞法分析器也只是狀態機器的一種應用。狀態機器比想象的廣的多的多。

      最後貼一下代碼,大部分想法都已經在那個文章裡說了,這裡只概略的總結一下:

方法一:遍曆鏈表,基本上要搜尋所有資料

// wenjianpaixu.cpp : Defines the entry point for the console application.<br />//<br />#include "stdafx.h"<br />#include <stdlib.h><br />#include <string.h><br />#include "math.h"<br />#include "time.h"<br />#include "windows.h"<br />typedef struct tag_Rec<br />{<br />unsigned int x;<br />unsigned int y;<br />unsigned int w;<br />unsigned int h;<br />unsigned int t;<br />tag_Rec* pNext;<br />}Rec;<br />int Compare(Rec r1,Rec r2)//r1是否在r2裡<br />{<br />bool b1=false,b2=false,b3=false,b4=false;<br />if (r1.x>r2.x&&r1.x<(r2.x+r2.w))<br />{<br />b1 = true;<br />}<br />if ((r1.x+r1.w)>r2.x&&(r1.x+r1.w)<(r2.x+r2.w))<br />{<br />b2=true;<br />}<br />if ((r1.y+r1.h)>r2.x&&(r1.y+r1.h)<(r2.y+r2.h))<br />{<br />b3 = true;<br />}<br />if (r1.y>r2.y&&r1.y<(r2.y+r2.h))<br />{<br />b4 = true;<br />}<br />if (b1&&b4)<br />{<br />return 1;<br />}<br />return 0;<br />}<br />//產生測試檔案<br />void ProduceTestFile()<br />{<br />FILE* fp= fopen("E://debug//myrec.txt","w");<br />char sText[256];<br />srand(NULL);<br />if (fp!=NULL)<br />{<br />int i = 0;<br />while (i<100000)<br />{<br />fprintf(fp,"%d,%d,%d,%d,%d/n",rand()*1024/65535,rand()*1024/65535,rand()*1024/65535,rand()*1024/65535,i);<br />i++;<br />}<br />}<br />fclose(fp);<br />}<br />//擷取一行的資料<br />int GetItem(FILE* pFile,Rec* pRec)<br />{<br />char sData;//儲存資料<br />char sInt[10];<br />memset(sInt,'/0',10);<br />int i = 0;<br />int iText = 0;<br />while ((sData=fgetc(pFile))!=EOF)<br />{<br />if (sData==','||sData=='/n')<br />{<br />switch(i)<br />{<br />case 0:<br />pRec->x = atoi(sInt);<br />break;<br />case 1:<br />pRec->y = atoi(sInt);<br />break;<br />case 2:<br />pRec->w = atoi(sInt);<br />break;<br />case 3:<br />pRec->h = atoi(sInt);<br />break;<br />case 4:<br />pRec->t = atoi(sInt);<br />break;<br />default:<br />return -1;<br />break;<br />}<br />if (sData=='/n')<br />{<br />return sData;<br />}<br />i++;<br />iText = 0;<br />memset(sInt,'/0',10);<br />}<br />else<br />{<br />if (iText<10)<br />{<br />sInt[iText]=sData;<br />}<br />else<br />{<br />return -1;<br />}<br />iText++;<br />}<br />}<br />pRec->t = atoi(sInt);<br />return sData;<br />}<br />void GetRecData(FILE* pFile,Rec* pRec)<br />{</p><p>/*int iRet = GetItem(pFile,pRec);//採用遞迴記憶體就會分配失敗<br />if (iRet==EOF||iRet==-1)<br />{<br />pRec->pNext = NULL;<br />}<br />else<br />{<br />pRec->pNext = new Rec;<br />GetRecData(pFile,pRec->pNext);<br />}*/<br />while(true)<br />{<br />int iRet = GetItem(pFile,pRec);<br />if (iRet==EOF||iRet==-1)<br />{<br />pRec->pNext = NULL;<br />break;<br />}<br />else<br />{<br />pRec->pNext = new Rec;<br />pRec = pRec->pNext;<br />}<br />}<br />}<br />//輸出資料<br />void PutData(Rec* pRec)<br />{<br />Rec* pNext=pRec;<br />while (pNext!=NULL)<br />{<br />printf("%d,%d,%d,%d,%d/n",pNext->x,pNext->y,pNext->w,pNext->h,pNext->t);<br />pNext = pNext->pNext;<br />}<br />}<br />//檢測資料<br />void TestData(Rec* pHead,Rec rT)<br />{<br />Rec* pNext = pHead;<br />int iRet = 0;<br />int iCount = 0;<br />while (pNext!=NULL)<br />{<br />iRet = Compare(*pNext,rT);<br />if (iRet)<br />{<br />//printf("%d,%d,%d,%d,%d/n",pNext->x,pNext->y,pNext->w,pNext->h,pNext->t);<br />iCount++;<br />}<br />pNext = pNext->pNext;</p><p>}<br />printf("共有%d/n",iCount);<br />}<br />//釋放記憶體<br />void ReleaseData(Rec* pHead)<br />{<br />/*if (pHead!=NULL)<br />{<br />Rec* pNext = pHead->pNext;<br />delete pHead;<br />ReleaseData(pNext);<br />}*/<br />Rec* pNext = pHead;<br />while (pNext)<br />{<br />pNext = pNext->pNext;<br />delete pHead;<br />pHead = pNext;<br />}<br />}<br />//解析檔案<br />int main(int argc, _TCHAR* argv[])<br />{<br />ProduceTestFile();<br />Rec* pHead = new Rec;<br />FILE* fp= fopen("E://debug//myrec.txt","r");<br />GetRecData(fp,pHead);<br />DWORD iTs = GetTickCount();<br />//PutData(pHead);<br />Rec recTest;<br />recTest.x = 100;<br />recTest.y = 100;<br />recTest.w = 800;<br />recTest.h = 100;<br />TestData(pHead,recTest);<br />DWORD iTe = GetTickCount();<br />printf("搜尋完成%d/n",iTe-iTs);<br />ReleaseData(pHead);<br />getchar();<br />return 0;<br />}<br />

方法二:數組+雜湊表+鏈地址處理衝突法

// wenjianpaixu.cpp : Defines the entry point for the console application.<br />//<br />#include "stdafx.h"<br />#include <stdlib.h><br />#include <string.h><br />#include "math.h"<br />#include "time.h"<br />#include "windows.h"<br />typedef struct tag_Rec<br />{<br />unsigned int x;<br />unsigned int y;<br />unsigned int w;<br />unsigned int h;<br />unsigned int t;<br />tag_Rec* pNext;<br />tag_Rec()<br />{<br />pNext = NULL;<br />}<br />}Rec;<br />Rec*** glPRecArr;//極座標的方法,將0-1024*1024範圍內分成1024個段<br />int Compare(Rec r1,Rec r2)//r1是否在r2裡<br />{<br />bool b1=false,b2=false,b3=false,b4=false;<br />if (r1.x>r2.x&&r1.x<(r2.x+r2.w))<br />{<br />b1 = true;<br />}<br />if ((r1.x+r1.w)>r2.x&&(r1.x+r1.w)<(r2.x+r2.w))<br />{<br />b2=true;<br />}<br />if ((r1.y+r1.h)>r2.x&&(r1.y+r1.h)<(r2.y+r2.h))<br />{<br />b3 = true;<br />}<br />if (r1.y>r2.y&&r1.y<(r2.y+r2.h))<br />{<br />b4 = true;<br />}<br />if (b1&&b4)<br />{<br />return 1;<br />}<br />return 0;<br />}<br />//產生測試檔案<br />void ProduceTestFile()<br />{<br />FILE* fp= fopen("E://debug//myrec.txt","w");<br />char sText[256];<br />srand(NULL);<br />if (fp!=NULL)<br />{<br />int i = 0;<br />while (i<1000000)<br />{<br />fprintf(fp,"%d,%d,%d,%d,%d/n",rand()*1024/65535,rand()*1024/65535,rand()*1024/65535,rand()*1024/65535,i);<br />i++;<br />}<br />}<br />fclose(fp);<br />}<br />//擷取一行的資料<br />int GetItem(FILE* pFile,Rec* pRec)<br />{<br />char sData;//儲存資料<br />char sInt[10];<br />memset(sInt,'/0',10);<br />int i = 0;<br />int iText = 0;<br />while ((sData=fgetc(pFile))!=EOF)<br />{<br />if (sData==','||sData=='/n')<br />{<br />switch(i)<br />{<br />case 0:<br />pRec->x = atoi(sInt);<br />break;<br />case 1:<br />pRec->y = atoi(sInt);<br />break;<br />case 2:<br />pRec->w = atoi(sInt);<br />break;<br />case 3:<br />pRec->h = atoi(sInt);<br />break;<br />case 4:<br />pRec->t = atoi(sInt);<br />break;<br />default:<br />return -1;<br />break;<br />}<br />if (sData=='/n')<br />{<br />return sData;<br />}<br />i++;<br />iText = 0;<br />memset(sInt,'/0',10);<br />}<br />else<br />{<br />if (iText<10)<br />{<br />sInt[iText]=sData;<br />}<br />else<br />{<br />return -1;<br />}<br />iText++;<br />}<br />}<br />pRec->t = atoi(sInt);<br />return sData;<br />}<br />void GetRecData(FILE* pFile)<br />{<br />//開闢空間,下三角數組<br />glPRecArr = new Rec**[1024];<br />for (int i = 0;i<1024;i++)<br />{<br />glPRecArr[i] = new Rec*[i+1];<br />}<br />//初始化<br />for (int i = 0;i<1024;i++)<br />{<br />for (int j=0;j<=i;j++)<br />{<br />glPRecArr[i][j]=NULL;<br />}<br />}<br />long lMaxPolar = 0;//最大極座標<br />long lMinPolar = 0;//最小極座標<br />unsigned int iMax = 0;//最大極座標儲存格<br />unsigned int iMin = 0;//最小極座標儲存格<br />Rec* pRecTemp=NULL;<br />while(true)<br />{<br />Rec* pRec = new Rec;<br />int iRet = GetItem(pFile,pRec);<br />//判斷資料存放區的位置<br />if (iRet==EOF||iRet==-1)<br />{<br />//pRec->pNext = NULL;<br />break;<br />}<br />else<br />{<br />/*pRec->pNext = new Rec;<br />pRec = pRec->pNext;*/<br />//根據最大極座標和最小極座標 確定儲存格<br />lMaxPolar = (pRec->x+pRec->w)*(pRec->x+pRec->w)+(pRec->y+pRec->h)*(pRec->y+pRec->h);//最大極座標的平方<br />lMinPolar = (pRec->x)*(pRec->x)+(pRec->y)*(pRec->y);//最小極座標的平方<br />//確定存放的儲存格<br />iMax = sqrt((double)lMaxPolar)/1024;//最大極座標分成1024段,確定最大極座標所在段數<br />iMin = sqrt((double)lMinPolar)/1024;//最小極座標分成1024段,確定最小極座標所在段數<br />if (iMax>=1024)<br />{<br />iMax = 1023;<br />}<br />if (iMin>=1024)<br />{<br />iMin = 1023;<br />}<br />//確定存放的位置<br />if (glPRecArr[iMax][iMin]==NULL)<br />{<br />glPRecArr[iMax][iMin] = pRec;<br />}<br />else<br />{<br />pRecTemp = glPRecArr[iMax][iMin]->pNext;//在該段數上,執行插入操作<br />glPRecArr[iMax][iMin]->pNext = pRec;<br />pRec->pNext = pRecTemp;<br />}<br />}<br />}<br />}<br />//檢測資料<br />void TestData(Rec rT)<br />{<br />long lMaxPolar = 0;//最大極座標<br />long lMinPolar = 0;//最小極座標<br />unsigned int iMax = 0;//最大極座標儲存格<br />unsigned int iMin = 0;//最小極座標儲存格<br />Rec* pRec = &rT;<br />lMaxPolar = (pRec->x+pRec->w)*(pRec->x+pRec->w)+(pRec->y+pRec->h)*(pRec->y+pRec->h);//最大極座標的平方<br />lMinPolar = (pRec->x)*(pRec->x)+(pRec->y)*(pRec->y);//最小極座標的平方<br />//確定存放的儲存格<br />iMax = sqrt((double)lMaxPolar)/1024;//最大極座標分成1024段<br />iMin = sqrt((double)lMinPolar)/1024;//最小極座標分成1024段<br />if (iMax>=1024)<br />{<br />iMax = 1023;<br />}<br />if (iMin>=1024)<br />{<br />iMin = 1023;<br />}<br />int iRet = 0;<br />int iCount = 0;<br />Rec* pNext = NULL;<br />for (int i = iMin;i<1024;i++)//它的最大的必須大於所有最小極座標<br />{<br />for (int j = 0;j<=iMax&&j<=i;j++)//它的最小的必須小於所有最大的<br />{<br />pNext = glPRecArr[i][j];<br />while (pNext!=NULL)<br />{<br />iRet = Compare(*pNext,rT);<br />if (iRet)<br />{<br />//printf("%d,%d,%d,%d,%d/n",pNext->x,pNext->y,pNext->w,pNext->h,pNext->t);//去掉這一行的i/o操作,搜尋時間少於1ms<br />iCount++;<br />}<br />pNext = pNext->pNext;<br />}<br />}<br />}</p><p>printf("共有%d/n",iCount);<br />}<br />//解析檔案<br />int main(int argc, _TCHAR* argv[])<br />{<br />ProduceTestFile();<br />//DWORD iTS = GetTickCount();<br />Rec* pHead = new Rec;<br />FILE* fp= fopen("E://debug//myrec.txt","r");<br />GetRecData(fp);<br />DWORD iTS = GetTickCount();<br />//PutData(pHead);<br />Rec recTest;<br />recTest.x = 400;<br />recTest.y = 100;<br />recTest.w = 800;<br />recTest.h = 100;<br />TestData(recTest);<br />DWORD iTE = GetTickCount();<br />printf("搜尋完成%d/n",iTE-iTS);<br />//ReleaseData(pHead);<br />getchar();<br />return 0;<br />}<br />

方法三:下三角數組+雜湊表+鏈地址處理衝突法

// wenjianpaixu.cpp : Defines the entry point for the console application.<br />//<br />#include "stdafx.h"<br />#include <stdlib.h><br />#include <string.h><br />#include "math.h"<br />#include "time.h"<br />#include "windows.h"<br />typedef struct tag_Rec<br />{<br />unsigned int x;<br />unsigned int y;<br />unsigned int w;<br />unsigned int h;<br />unsigned int t;<br />tag_Rec* pNext;<br />tag_Rec()<br />{<br />pNext = NULL;<br />}<br />}Rec;<br />Rec*** glPRecArr;//極座標的方法,將0-1024*1024範圍內分成1024個段<br />int Compare(Rec r1,Rec r2)//r1是否在r2裡<br />{<br />bool b1=false,b2=false,b3=false,b4=false;<br />if (r1.x>r2.x&&r1.x<(r2.x+r2.w))<br />{<br />b1 = true;<br />}<br />if ((r1.x+r1.w)>r2.x&&(r1.x+r1.w)<(r2.x+r2.w))<br />{<br />b2=true;<br />}<br />if ((r1.y+r1.h)>r2.x&&(r1.y+r1.h)<(r2.y+r2.h))<br />{<br />b3 = true;<br />}<br />if (r1.y>r2.y&&r1.y<(r2.y+r2.h))<br />{<br />b4 = true;<br />}<br />if (b1&&b4)<br />{<br />return 1;<br />}<br />return 0;<br />}<br />//產生測試檔案<br />void ProduceTestFile()<br />{<br />FILE* fp= fopen("E://debug//myrec.txt","w");<br />char sText[256];<br />srand(NULL);<br />if (fp!=NULL)<br />{<br />int i = 0;<br />while (i<1000000)<br />{<br />fprintf(fp,"%d,%d,%d,%d,%d/n",rand()*1024/65535,rand()*1024/65535,rand()*1024/65535,rand()*1024/65535,i);<br />i++;<br />}<br />}<br />fclose(fp);<br />}<br />//擷取一行的資料<br />int GetItem(FILE* pFile,Rec* pRec)<br />{<br />char sData;//儲存資料<br />char sInt[10];<br />memset(sInt,'/0',10);<br />int i = 0;<br />int iText = 0;<br />while ((sData=fgetc(pFile))!=EOF)<br />{<br />if (sData==','||sData=='/n')<br />{<br />switch(i)<br />{<br />case 0:<br />pRec->x = atoi(sInt);<br />break;<br />case 1:<br />pRec->y = atoi(sInt);<br />break;<br />case 2:<br />pRec->w = atoi(sInt);<br />break;<br />case 3:<br />pRec->h = atoi(sInt);<br />break;<br />case 4:<br />pRec->t = atoi(sInt);<br />break;<br />default:<br />return -1;<br />break;<br />}<br />if (sData=='/n')<br />{<br />return sData;<br />}<br />i++;<br />iText = 0;<br />memset(sInt,'/0',10);<br />}<br />else<br />{<br />if (iText<10)<br />{<br />sInt[iText]=sData;<br />}<br />else<br />{<br />return -1;<br />}<br />iText++;<br />}<br />}<br />pRec->t = atoi(sInt);<br />return sData;<br />}<br />void GetRecData(FILE* pFile)<br />{<br />//開闢空間,下三角數組<br />glPRecArr = new Rec**[1024];<br />for (int i = 0;i<1024;i++)<br />{<br />glPRecArr[i] = new Rec*[i+1];<br />}<br />//初始化<br />for (int i = 0;i<1024;i++)<br />{<br />for (int j=0;j<=i;j++)<br />{<br />glPRecArr[i][j]=NULL;<br />}<br />}<br />long lMaxPolar = 0;//最大極座標<br />long lMinPolar = 0;//最小極座標<br />unsigned int iMax = 0;//最大極座標儲存格<br />unsigned int iMin = 0;//最小極座標儲存格<br />Rec* pRecTemp=NULL;<br />while(true)<br />{<br />Rec* pRec = new Rec;<br />int iRet = GetItem(pFile,pRec);<br />//判斷資料存放區的位置<br />if (iRet==EOF||iRet==-1)<br />{<br />//pRec->pNext = NULL;<br />break;<br />}<br />else<br />{<br />/*pRec->pNext = new Rec;<br />pRec = pRec->pNext;*/<br />//根據最大極座標和最小極座標 確定儲存格<br />lMaxPolar = (pRec->x+pRec->w)*(pRec->x+pRec->w)+(pRec->y+pRec->h)*(pRec->y+pRec->h);//最大極座標的平方<br />lMinPolar = (pRec->x)*(pRec->x)+(pRec->y)*(pRec->y);//最小極座標的平方<br />//確定存放的儲存格<br />iMax = sqrt((double)lMaxPolar)/1024;//最大極座標分成1024段,確定最大極座標所在段數<br />iMin = sqrt((double)lMinPolar)/1024;//最小極座標分成1024段,確定最小極座標所在段數<br />if (iMax>=1024)<br />{<br />iMax = 1023;<br />}<br />if (iMin>=1024)<br />{<br />iMin = 1023;<br />}<br />//確定存放的位置<br />if (glPRecArr[iMax][iMin]==NULL)<br />{<br />glPRecArr[iMax][iMin] = pRec;<br />}<br />else<br />{<br />pRecTemp = glPRecArr[iMax][iMin]->pNext;//在該段數上,執行插入操作<br />glPRecArr[iMax][iMin]->pNext = pRec;<br />pRec->pNext = pRecTemp;<br />}<br />}<br />}<br />}<br />//檢測資料<br />void TestData(Rec rT)<br />{<br />long lMaxPolar = 0;//最大極座標<br />long lMinPolar = 0;//最小極座標<br />unsigned int iMax = 0;//最大極座標儲存格<br />unsigned int iMin = 0;//最小極座標儲存格<br />Rec* pRec = &rT;<br />lMaxPolar = (pRec->x+pRec->w)*(pRec->x+pRec->w)+(pRec->y+pRec->h)*(pRec->y+pRec->h);//最大極座標的平方<br />lMinPolar = (pRec->x)*(pRec->x)+(pRec->y)*(pRec->y);//最小極座標的平方<br />//確定存放的儲存格<br />iMax = sqrt((double)lMaxPolar)/1024;//最大極座標分成1024段<br />iMin = sqrt((double)lMinPolar)/1024;//最小極座標分成1024段<br />if (iMax>=1024)<br />{<br />iMax = 1023;<br />}<br />if (iMin>=1024)<br />{<br />iMin = 1023;<br />}<br />int iRet = 0;<br />int iCount = 0;<br />Rec* pNext = NULL;<br />for (int i = iMin;i<1024;i++)//它的最大的必須大於所有最小極座標<br />{<br />for (int j = 0;j<=iMax&&j<=i;j++)//它的最小的必須小於所有最大的<br />{<br />pNext = glPRecArr[i][j];<br />while (pNext!=NULL)<br />{<br />iRet = Compare(*pNext,rT);<br />if (iRet)<br />{<br />iCount++;<br />}<br />pNext = pNext->pNext;<br />}<br />}<br />}</p><p>printf("共有%d/n",iCount);<br />}<br />//解析檔案<br />int main(int argc, _TCHAR* argv[])<br />{<br />ProduceTestFile();<br />//DWORD iTS = GetTickCount();<br />Rec* pHead = new Rec;<br />FILE* fp= fopen("E://debug//myrec.txt","r");<br />GetRecData(fp);<br />DWORD iTS = GetTickCount();<br />//PutData(pHead);<br />Rec recTest;<br />recTest.x = 400;<br />recTest.y = 100;<br />recTest.w = 800;<br />recTest.h = 100;<br />TestData(recTest);<br />DWORD iTE = GetTickCount();<br />printf("搜尋完成%d/n",iTE-iTS);<br />//ReleaseData(pHead);<br />getchar();<br />return 0;<br />}<br />

如果在大資料量下,如果資料結構處理的不好,計算量將會被放大,也就是說最笨的方法計算量可能是一千六百萬次計算

 

痛苦是有的,快樂也是有的!

發現一個秘密,我只要晚上幹正事,老婆就不會要求我刷碗,哈哈

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.