Play with the long arrow --> and overload it
Tags: cpp
Published: 2023-04-11 07:50:00

---
title: Play with the long arrow --> and overload it
published: true
description: -> is for normies, the cool girls are using -->
tags: cpp
cover_image: https://dev-to-uploads.s3.amazonaws.com/uploads/articles/u7uxw0178t5y0e4lfft5.jpg
---

## Article::Article
Have you ever heard of the person who thought they found a new operator `-->`. If you haven't, look at this [Stack Overflow thread](https://stackoverflow.com/questions/1642028/what-is-the-operator-in-c) and read the responses (except the validated and boring one), it is pretty hilarious.

Anyway, wouldn't it be cool if we could create new operators like they can do [in Swift](https://betterprogramming.pub/how-to-create-an-operator-in-swift-585d81ff0a84). A part of me want to learn Swift just for this feature, even if I am not a mobile dev and that I don't even have a Mac or an iPhone.

But in C++ we can't... or can we? Well, we can't create operators from scratch, but we can combine existing operators.

![DBZ fusion between operator -- and operator > to create a new super operator -->](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/u7uxw0178t5y0e4lfft5.jpg)

In this article, we'll see how to make funny thing with a long arrow `-->`.

## The idea
When we write: `x-->0`, it is just the combination of the post decrement operator and then a comparison operator and both are overloadable.

![meme template: Anthony Adams Rubbing Hands. Me when I see that an operator is overloadable](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/2twrip4krbe9j6f0siy6.jpg)

It means that that if we overload the operator `--`, returns something, and that something we return have the operator `>` overloaded, even if we technically are not overloading an operator `-->` it feels a bit like it.

## Example
If you want to have a counter, and you want to target a specific value, you could do this:
```C++
#include <iostream>

struct Counter
{
	auto operator --(int)
	{
        struct Tmp
        {
            auto operator>(int destination)
            {
                if (c.i == destination)
                {
                    return false;
                }
                else
                {
                    c.i += (c.i > destination) ? -1 : 1;
                    return true;
                }
            }

            Counter& c;
        };

        return Tmp{*this};
		
	}

	int i;
};

int main(int, char **)
{
	Counter c{10};
	while (c-->15)
	{
		std::cout << c.i << std::endl;
	}
}
```
[Compiler explorer link](https://godbolt.org/z/xE77h5Gba)

## Mess with your colleagues
If you want to mess with your colleagues or make a good April fool's joke, just send them this code with this [link on Compiler Explorer](https://godbolt.org/z/bWavfxEh4) and make them believe that the operator `-->` was added to the standard and that it is named `to` (in the same way that the operator `&&` is called `and` and that you can write `and` instead of `&&`):
```C++
// This code is almost the same as the snippet above, 
#include <type_traits>
#include <concepts>
#include <iostream>

struct Counter
{
	auto operator to(int destination)
	{
		if (i == destination)
		{
			return false;
		}
		else
		{
			i += (i > destination) ? -1 : 1;
			return true;
		}
	}

	int i;
};

int main(int, char **)
{
	Counter c{10};
	while (c-->15)
	{
		std::cout << c.i << std::endl;
	}
}
```

I promise you it will be fun, I have done it and even if almost no one felt into the trap, they still scratched their head to understand how I made this snippet.

## Implement the unified call syntax with it
If you haven't read [my article about unified call syntax](https://dev.to/baduit/my-first-attempt-to-simulate-the-unified-call-syntax-5892), I advise you to read it to understand this section.

To summarize the previous article, I used the operator ->* to be able to do that:
```C++
#include <iostream>
#include <vector>
#include <algorithm>

#include <unic/unic.hpp>

int main()
{
	using unic::operator->*;
	constexpr auto find = UNIC_GENERATE_PROXY(std::ranges::find);
	std::vector ints = { 1, 2, 3, 4, 5 };

	auto it = ints->*find(3);
	if (it != ints.cend())
		std::cout << "Found : " << *it << std::endl;
	else
		std::cout << "Not found :'(" << std::endl;
}
```
And wrote a [little library](https://github.com/Baduit/Unic) about it.

I did almost the same for the long arrow `-->` and wrote another little library named [long_arrow](https://github.com/Baduit/long_arrow) (Yes, I know, I was not very inspired for the name). With it you can do that:
```C++
#include <iostream>
#include <long_arrow/long_arrow.hpp>

LONG_ARROW_GENERATE_OPERATOR_POST_DECREMENT(std::string)

constexpr std::string concat_const(const std::string& str, char c)
{
	return str + c;
}

constexpr void concat_mut(std::string& str, char c)
{
	str += c;
}

constexpr std::string concat_rvalue(std::string&& str, char c)
{
	return std::move(str += c);
}

int main()
{
	using long_arrow::operator>;

	{
		auto concat = LONG_ARROW_GENERATE_PROXY(concat_const);
		std::string str = "Hell";
		std::string res = str-->concat('o');
		std::cout << res << std::endl; // Hello
	}
	{
		auto concat = LONG_ARROW_GENERATE_PROXY(concat_mut);
		std::string str = "Hell";
		str-->concat('o');
		std::cout << str << std::endl;
	}
	{
		auto concat = LONG_ARROW_GENERATE_PROXY(concat_rvalue);
		std::string str = std::string("Hell")-->concat('o');
		std::cout << str << std::endl;
	}
}
```
I won't go into the detail because I could write a little article about it, I just wanted to show an example of what it is possible to do with the long arrow.

## Article::~Article
I hope you had as much fun reading this article as I got writing it!    
It is another article where I showed you that you can do funny stuff and play with the C++ syntax. Also, that's not because something is possible that you should do it, I don't see the "operator `-->`" useful except maybe if you are creating a [DSL](https://en.wikipedia.org/wiki/Domain-specific_language) (domain specific language) in C++.

Oh and don't forget to tell me if you have found how I made the snippet to mess with the colleagues works! I'm really proud of how hard it is to see it haha.


## Sources
* [https://stackoverflow.com/questions/1642028/what-is-the-operator-in-c](https://stackoverflow.com/questions/1642028/what-is-the-operator-in-c)
* [https://betterprogramming.pub/how-to-create-an-operator-in-swift-585d81ff0a84](https://betterprogramming.pub/how-to-create-an-operator-in-swift-585d81ff0a84)