package com.git.edismax;
import java.io.ioexception;
import org.apache.solr.client.solrj.solrclient;
import org.apache.solr.client.solrj.solrquery;
import org.apache.solr.client.solrj.solrserverexception;
import org.apache.solr.client.solrj.solrquery.order;
import org.apache.solr.client.solrj.impl.httpsolrclient;
import org.apache.solr.client.solrj.response.queryresponse;
import org.apache.solr.common.solrdocument;
import org.apache.solr.common.solrdocumentlist;
import org.apache.solr.common.params.commonparams;
/**
* 測試edismax的代碼實作自定義權重排序股則
* @author songqinghu
*
*/
public class scorebyedismax {
private final static string baseurl = "http://localhost:8983/solr/dismax";
public static void main(string[] args) throws exception{
scorebysum() ;
system.out.println("=====分割線==========");
scorebyproportion();
}
/**
*
* @描述:按照各個數值的比重來進行權重計算 count 10% point 45% hot 45% --假設總分為100分 那麼 分别最大分為 10 45 45
* @return void
* @exception
* @createtime:2016年4月18日
* @author: songqinghu
* @throws ioexception
* @throws solrserverexception
*/
public static void scorebyproportion() throws solrserverexception, ioexception{
//先查詢出來三個字段中每個字段的最大值--編寫好計算權重的公式---實際項目中應該還要加入是否存在的判斷
long countmax = getmaxforfield("count");
long pointmax = getmaxforfield("point");
long hotmax = getmaxforfield("hot");
string scoremethod = "sum(product(div(count,"+countmax+"),10),product(div(point,"+pointmax+"),45),product(div(hot,"+hotmax+"),45))^1000000000";
solrquery query = new solrquery();
query.set(commonparams.q, "國美*");
query.set(commonparams.fl,"id","name","count","point","hot","score");
query.set("deftype","edismax");
query.set("bf", scoremethod);
queryresponse response = getclient().query(query);
resultshow(response);
* @描述:xxxxxxx
* @return
* @return long
private static long getmaxforfield(string fieldname) throws solrserverexception, ioexception{
solrquery query = new solrquery();
query.set(commonparams.q, "*:*");
query.set(commonparams.fl, fieldname);
query.setsort(fieldname, order.desc);
query.setrows(1);
queryresponse countresponse = getclient().query(query);
solrdocument maxcount = countresponse.getresults().get(0);
long result = (long) maxcount.getfieldvalue(fieldname);
system.out.println(fieldname + ":" + result);
return result;
* @描述:按照 count point 和 hot 的 和的數量來進行權重計算
public static void scorebysum() throws solrserverexception, ioexception{
solrquery query = new solrquery();
//開啟edismax方式來進行自定義權重算法
query.set("deftype", "edismax");
query.set("bf","sum(count,point,hot)^1000000000");
* @描述:查詢結果顯示類
* @param response
private static void resultshow(queryresponse response){
int time = response.getqtime();
system.out.println("響應時間:"+ time+"ms");
solrdocumentlist results = response.getresults();
long numfound = results.getnumfound();
system.out.println("總數量:"+numfound);
for (solrdocument doc : results) {
system.out.println("id:"+ doc.getfieldvalue("id").tostring());
system.out.println("name:"+ doc.getfieldvalue("name").tostring());
system.out.println("count:"+ doc.getfieldvalue("count").tostring());
system.out.println("point:"+ doc.getfieldvalue("point").tostring());
system.out.println("hot:"+ doc.getfieldvalue("hot").tostring());
system.out.println("score:"+ doc.getfieldvalue("score").tostring());
system.out.println();
}
* @描述:擷取單機版本的連接配接資訊
* @return solrclient
public static solrclient getclient(){
solrclient solrclient = new httpsolrclient(baseurl);
return solrclient;
}

執行結果:
響應時間:1ms
總數量:6
id:6
name:國美手機
count:2314
point:1123
hot:717
score:4154.0
id:1
name:國美集團
count:5
point:4
hot:3
score:12.0
id:5
name:國美美信
count:1
point:5
hot:4
score:10.0
id:2
name:國美電器
count:4
point:3
hot:2
score:9.0
id:4
name:國美金融
count:2
point:1
hot:5
score:8.0
id:3
name:國美線上
count:3
point:2
hot:1
score:6.0
=====分割線==========
響應時間:2ms
score:100.0
score:0.45572376
score:0.3701771
score:0.36252183
score:0.26302284
score:0.15586855
權重計算分析:
權重影響參數設定表:
主查詢權重*自定義權重
查詢主條件比例
權重公式比例
solr計算
自己計算
^1
^100000000
0.45572376
0.45572373506010969850068170504362
^1000000000000
^0.0000000001
實踐得出 這裡score的計算是兩部分組成 一個是主查詢的權重比對值還有一個是自己設定的權重計算
可以使其中一個無限的趨近于一個最大值或者最小值但是不能使之為0
看到不去刻意的改變solr自身的兩部分打分機制,其打分結果和理想的誤差為0.025*0.000001 這個誤差,一般情況應該都是能滿足的,不影響結果的