# Sort based on absolute value

**URL:** <https://discuss.elastic.co/t/sort-based-on-absolute-value/328078>\
**Category:** Elasticsearch\
**Created:** [March 20, 2023, 1:34pm UTC](https://discuss.elastic.co/t/sort-based-on-absolute-value/328078 "2023-03-20T13:34:48Z")\
**Posts on this page:** 7\
**Page:** 1

<div class="post-metadata">

**Author:** ![\_baba](https://avatars.discourse-cdn.com/v4/letter/_/ecb155/32.png) [@\_baba](https://discuss.elastic.co/u/_baba)\
**Post date:** [March 20, 2023, 1:34pm UTC](https://discuss.elastic.co/t/sort-based-on-absolute-value/328078/1 "2023-03-20T13:34:48Z")

</div>

Hi, I'm looking to sort documents based on a field of long type by their absolute value.

So, the change field has both positive and negative numbers.

"change" : {  
"type" : "long"  
}

I want to sort it in such a way that if change = -23 and change = 23, -23 gets the preference, but if change = 45 and 50, 50 gets the preference.

---

<div class="post-metadata">

**Author:** ![RabBit\_BR](https://sea2.discourse-cdn.com/elastic/user_avatar/discuss.elastic.co/rabbit_br/32/82261_2.png) [@RabBit\_BR](https://discuss.elastic.co/u/RabBit_BR)\
**Post date:** [March 20, 2023, 1:45pm UTC](https://discuss.elastic.co/t/sort-based-on-absolute-value/328078/2 "2023-03-20T13:45:20Z")

</div>

Hi @_baba

Set the "order" not work?

```auto
    "sort":[
        {
        "change": {"order" : "desc"}
        }
    ]

```

---

<div class="post-metadata">

**Author:** ![\_baba](https://avatars.discourse-cdn.com/v4/letter/_/ecb155/32.png) [@\_baba](https://discuss.elastic.co/u/_baba)\
**Post date:** [March 20, 2023, 4:04pm UTC](https://discuss.elastic.co/t/sort-based-on-absolute-value/328078/3 "2023-03-20T16:04:44Z")

</div>

for the data sets [-23, 23, 45, 50], this query will result [50, 45, 23, -23]. I'm looking for this order [50, 45, -23, 23].  
so basically, if there is a tie in 23 and -23, (-)23 has the precedence, otherwise it should be desc order.

---

<div class="post-metadata">

**Author:** ![RabBit\_BR](https://sea2.discourse-cdn.com/elastic/user_avatar/discuss.elastic.co/rabbit_br/32/82261_2.png) [@RabBit\_BR](https://discuss.elastic.co/u/RabBit_BR)\
**Post date:** [March 20, 2023, 4:52pm UTC](https://discuss.elastic.co/t/sort-based-on-absolute-value/328078/4 "2023-03-20T16:52:14Z")

</div>

I don't believe this is possible even using sort script.

---

<div class="post-metadata">

**Author:** ![stu](https://sea2.discourse-cdn.com/elastic/user_avatar/discuss.elastic.co/stu/32/75063_2.png) [@stu](https://discuss.elastic.co/u/stu)\
**Post date:** [March 20, 2023, 7:17pm UTC](https://discuss.elastic.co/t/sort-based-on-absolute-value/328078/5 "2023-03-20T19:17:12Z")

</div>

Hi @_baba.

> so basically, if there is a tie in 23 and -23, (-)23 has the precedence, otherwise it should be desc order.

You can write a [sort script](https://www.elastic.co/guide/en/elasticsearch/reference/current/sort-search-results.html#script-based-sorting) to do this.

You'd have to pick scores such that the score for -23 is higher than 23.

How about making the score two times the absolute value of `change`? The scores for -23 and 23 would be `46`.  
Then, we can add one if `change` is negative. So, -23 would score `47` while 23 would still score `46`.

Multiplying by two ensures adjacent numbers are at two least scores away.

```auto
# setup
PUT sort
{
  "mappings": {
    "properties": {
      "change": {
        "type": "integer"
      }
    }
  }
}

PUT sort/_bulk
{"index": {"_id":1}}
{"change":-23}
{"index": {"_id":2}}
{"change":23}
{"index": {"_id":3}}
{"change":45}
{"index": {"_id":4}}
{"change":50}

```

```auto
GET sort/_search
{
  "query": {
    "match_all": {}
  },
  "sort": {
    "_script": {
      "type": "number",
      "script": {
        "source": """
        if (doc['change'].empty) {
          return 0;
        }
        def change = doc['change'].value;
        if (change >= 0) {
          return change * 2;
        }
        return (change * -1 * 2) + 1;
        """
      },
      "order": "desc"
    }
  }
}

```

```auto
# result
{
  "took" : 7,
  "timed_out" : false,
  "_shards" : {
    "total" : 1,
    "successful" : 1,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : {
      "value" : 4,
      "relation" : "eq"
    },
    "max_score" : null,
    "hits" : [
      {
        "_index" : "sort",
        "_id" : "4",
        "_score" : null,
        "_source" : {
          "change" : 50
        },
        "sort" : [
          100.0
        ]
      },
      {
        "_index" : "sort",
        "_id" : "3",
        "_score" : null,
        "_source" : {
          "change" : 45
        },
        "sort" : [
          90.0
        ]
      },
      {
        "_index" : "sort",
        "_id" : "1",
        "_score" : null,
        "_source" : {
          "change" : -23
        },
        "sort" : [
          47.0 # (23 * 2) + 1 because change is negative
        ]
      },
      {
        "_index" : "sort",
        "_id" : "2",
        "_score" : null,
        "_source" : {
          "change" : 23
        },
        "sort" : [
          46.0
        ]
      }
    ]
  }
}

```

---

<div class="post-metadata">

**Author:** ![\_baba](https://avatars.discourse-cdn.com/v4/letter/_/ecb155/32.png) [@\_baba](https://discuss.elastic.co/u/_baba)\
**Post date:** [March 21, 2023, 5:36am UTC](https://discuss.elastic.co/t/sort-based-on-absolute-value/328078/6 "2023-03-21T05:36:07Z")

</div>

Thanks for sharing this.

---

<div class="post-metadata">

**Author:** ![system](https://us1.discourse-cdn.com/elastic/original/3X/1/a/1ac57faf039f6b580b3f104ef42a2a89e41014de.png) [@system](https://discuss.elastic.co/u/system)\
**Post date:** [April 18, 2023, 5:36am UTC](https://discuss.elastic.co/t/sort-based-on-absolute-value/328078/7 "2023-04-18T05:36:46Z")

</div>

This topic was automatically closed 28 days after the last reply. New replies are no longer allowed.
