#include <bit>
#include <bitset>
#include <assert.h>
#include <stdio.h>
#include <string.h>
#include <algorithm>
#include <sstream>
#include <iostream>
#include <set>
#include <map>
#include <vector>
#include <math.h>
#include <stdlib.h>
#include <queue>
#include <stack>
#include <iomanip>

typedef long double ld;
typedef long long ll;

using namespace std;

ll MOD = ((ll)1e9 + 7);

struct mod {
	ll x;

	mod(ll tx = 0) {
		x = tx;
	}
	
	mod& operator=(const ll & tx) {
		x = tx;
		return *this;
	}
	
	mod& operator=(const mod & m2) {
		x = m2.x;
		return *this;
	}

	mod operator+(const mod& m2) const {
		return (x + m2.x) % MOD;
	}

	mod& operator+=(const mod& m2) {
		x += m2.x;
		x %= MOD;
		return *this;
	}

	mod operator-(const mod & m2) const {
		return (x - m2.x + MOD) % MOD;
	}

	mod& operator-=(const mod & m2) {
		x -= m2.x;
		x = (x + MOD) % MOD;
		return *this;
	}

	mod operator*(const mod & m2) const {
		return (x * m2.x) % MOD;
	}

	mod& operator*=(const mod & m2) {
		x *= m2.x;
		x %= MOD;
		return *this;
	}

	mod mypow(ll k) const {
		mod ret = 1;
		mod cur = x;
		while (k) {
			if (k & 1) {
				ret *= cur;
			}
			cur *= cur;
			k >>= 1;
		}
		return ret;
	}

	mod inv() const {
		return mypow(MOD - 2);
	}

	mod operator/(const mod & m2) const {
		return mod(((*this).x * m2.inv().x) % MOD);
	}

	mod& operator/=(const mod & m2) {
		x *= m2.inv().x;
		x %= MOD;
		return *this;
	}

	bool operator<(const mod & m2) const {
		return x < m2.x;
	}
};

ostream &operator<<(ostream & os, const mod & m) {
	return os << m.x;
}

/* TEMPLATE ENDS HERE */

#define MAXN (1 << 20)

vector<ll> pos, neg;
ll a[MAXN];
ll n;
vector<pair<ll, ll> > ans;

int main() {
	cout << fixed << setprecision(12);	
	cin >> n;
	for (ll i = 0; i < n; i++) {
		cin >> a[i];
		if (a[i] >= 0) {
			pos.push_back(a[i]);
		} else if (a[i] < 0) {
			neg.push_back(a[i]);
		} 
	}
	sort(pos.begin(), pos.end());
	sort(neg.begin(), neg.end(), greater<ll>());
	ll sol;
	for (int i = 0; i < n; i++) {
		sol += llabs(a[i]);
	}
	if (pos.size() && neg.size()) {
		ll nn = neg[0];
		ll pp = pos[0];
		for (ll i = 1; i < (ll)pos.size(); i++) {
			ans.push_back(make_pair(nn, pos[i]));
			nn -= pos[i];
		}
		for (ll i = 1; i < (ll)neg.size(); i++) {
			ans.push_back(make_pair(pp, neg[i]));
			pp -= neg[i];
		}
		ans.push_back(make_pair(pp, nn));
	} else if (pos.size()) {
		ll nn = pos[0];
		for (ll i = 1; i < (ll)pos.size() - 1; i++) {
			ans.push_back(make_pair(nn, pos[i]));
			nn -= pos[i];
		}
		ans.push_back(make_pair(pos[(ll)pos.size() - 1], nn));
		sol -= 2 * pos[0];
	} else if (neg.size()) {
		ll nn = neg[0];
		for (ll i = 1; i < (ll)neg.size(); i++) {
			ans.push_back(make_pair(nn, neg[i]));
			nn -= neg[i];
		}
		sol += 2 * neg[0];
	}
	pair<ll, ll> last = ans[(ll)ans.size() - 1];
	ll sol2 = last.first - last.second;
	cout << sol2 << endl;
	//cerr << sol << endl;
	if (sol != sol2) {
		if (pos.size() && neg.size()) {
			while (1) {
				sol++;
			}
		} else if (pos.size()) {
			sol = sol / 0;
		} else if (neg.size()){
			int * foo;
			while (1) {
				foo = new int[1000000];
			}
		}
	}
	for (ll i = 0; i < ans.size(); i++) {
		cout << ans[i].first << " " << ans[i].second << endl;
	}
	return 0;
}


Measured memory_bytes: 7840