1 Introduction and Motivation for 'portsort'

Portfolio sorts have been a key part of empirical financial research since the 1970s. Sorting procedures are used extensively in identifying and exploring relationships between expected returns and asset class characteristics. The portfolio sorting approach has become widely used and is currently the dominant approach in empirical finance to test for and establish cross-sectional relationships between expected asset returns and asset characteristics. Past empirical work featuring portfolio sorts include the use of price-to-earnings ratios @basu1977investment, book-to-market values @fama1992cross, firm size @banz1981relationship, volatility @ang2006cross, cross-sectional momentum @jegadeesh1993returns and host of over featuring factors such as liquidity, default risk and downside risk (Value-at-Risk, Lower Partial Moments etc.).

The portsort R package includes functionality for both a conditional sort and an unconditional sort up to the third dimension, i.e assets can be grouped by up to three factors. After the sorting procedure has been conducted, there is further functionality to analyse the turnover, relative frequency of the assets in each sub-portfolio and the mean sub-portfolio size.

The generic approach in empirical finance is to first sort assets based on some factor into multiple sub-portfolios at some formation point and then examine the out-of-sample performance of these sub-portfolios. Often, long-short zero-cost portfolios are constructed by initiating positions in the top and bottom sub-portfolios (in the case of a univariate sort). The portsort package simplifies this process by allowing the user to automatically backtest univariate, double and triple-sorted portfolios. The output of the core sorting functions includes the out-of-sample sub-portfolio returns and a list of the assets in each sub-portfolio. From this, you can create trading strategies (long-short portfolios), pass the sub-portfolios to a regression analysis or conduct further analysis on the sub-portfolios themselves. The primary goal of the package is to offer academic researchers, students and practitioners an easy way to conduct the portfolio sort procedure.

2 Conducting Conditional and Unconditional Sorts

The portsort package offers functionality for both a conditional and unconditional sort - a concept that is still, for unknown reasons, glossed over by most lecturers in undergraduate and MBA financial economics coursework. The differences can be profound and have a major impact on the out-of-sample portfolio results. In the case of a univariate portfolio sort, the results are identical, however, higher dimension sorts will differ markedly.

2.1 Conditional Sorting Procedure

The conditional sorting procedure is best explained by example. Assume an asset manager has identified two stock factors which he/she thinks are drivers of expected stock returns due to prior statistical analysis. Let factor one (Fa) be market capitalization and factor two (Fb) be the book-to-market ratio. A conditional double sort strongly depends on which factor the asset manager decides to sort the stocks by first. Let us assume that the manager thinks that market capitalization has a stronger effect on expected returns. At time t, stocks are first sorted into n sub-portfolios based on market capitalization. Instead of using quantile break-points, the manager decides to form 3 sub-portfolios (tercile portfolios). The result is 3 sub-portfolios sorted from low to high based on market capitalization (a basic univariate sort). Now, within these 3 sub-portfolios, the manager decides to sort each sub-portfolio into a further m sub-portfolios based on the book-to-market ratio. Let us assume the manager decides on terciles for ease of interpretation. This means that the stocks within each market capitalization sub-portfolio are further sorted from low to high resulting in 3 book-to-market sorted sub-portfolios within the market capitalization sorted sub-portfolio tercile. Overall, 9 sub-portfolios are formed (there are 3 book-to-market sorted portfolios within each market capitalization sorted tercile). Any arbitrary number of sub-portfolios can be constructed based on the dimensions of each sort. The maximum amount of sub-portfolios in the case of a double sort is n x m and in the case of a triple sort n x m x z.

2.2 Unconditional Sorting Procedure

In an unconditional sort, the order of the sort does not matter, i.e the manager will get the same results regardless of the sort order. Using the example above, Fa and Fb are sorted independently (at the same time) into terciles. This results in 'Sort 1' which is the stock universe sorted by market capitalization from low to high. These same stocks (regardless of the first sort) are sorted into book-to-market terciles called 'Sort 2'. We now have two univariate sorts stored in tercile portfolios which are sorted independently of each other. This is the crucial difference between a conditional and unconditional sort - the double or triple sorting procedure is based on the intersection between each sub-portfolio (in this case terciles). For example, if stock 1, 23 and 40 is in the 1st market capitalization tercile, while stock 1, 20 and 43 is in the 1st book-to-market tercile, the 'L1-L1' sub-portfolio would only contain stock 1 and stock 43. The result is that each sub-portfolio will contain stocks that are the intersection of each independently sorted sub-portfolio.

2.3 Impact on Sub-Portfolios

The key difference between the two sorting procedures is that in a conditional sort, the factor which is sorted on first impacts the second sort. This means that the sub-portfolios formed within the portfolios formed by the first sort are 'conditional' on the first factor. This may seem obvious, but will result in large differences between sub-portfolios formed in the unconditional sorting process. In the case of the conditional sort, the factor that is sorted on first will have a much greater influence on forward returns than the the other factors that are subsequently sorted conditional on the first factor sort.

3. Functions included in portsort

3.1 conditional.sort and unconditional.sort

Both functions compute either a univariate, double or triple dimension sort. Function output includes an xts object of sub-portfolio returns and a list of the sub-portfolios. Both the conditional and unconditional sorts are pre-built to sort from low to high so that the interpretation of the out-of-sample return xts object is easier. For example, a double sort with dimension 3 x 3 (i.e there are 3 break-points for each factor) is conducted with Fa and Fb. A graphical depiction of the sort is shown below:

The out-of-sample returns for each sub-portfolio are stored in columns 1 to 9 of the output matrix. Column 1 includes the returns for the 'Low-Low' sub-portfolio, column 4 includes returns for the 'Mid-Low' sub-portfolio whilst column 9 includes the 'High-High' sub-portfolio returns. The dimension of each sort can be defined with user-defined break-points.

3.2 portfolio.turnover

The portfolio.turnover function takes the output of either the conditional or unconditional sort and returns a list which includes an xts object with the turnovers for each rebalancing period and the mean turnover for each asset over time.

3.3 portfolio.frequency

The portfolio.frequency functions takes as input a rank and the output of one of the sorting functions. The function computes how many times a given asset appeared in every sub-portfolio based on the rank input.

4 Empirical Example using Cryptocurrencies

4.1 Univariate Sort with Cross-Sectional Momentum

Cross-sectional momentum was popularized by @jegadeesh1993returns. First, an asset's return momentum is computed by summing the asset's log return over the prior s-periods. A skip period k is often used to remove the prior k-periods to account for possible short-term reversals. A cross-sectional momentum strategy using the methodology of @jegadeesh1993returns can easily be constructed using the functionality of portsort.

# Following the methodology of Jegadeesh and Titman, 1993, we will now form a long-short, zero-cost portfolio which initiates a long position in the high momentum sub-portfolio (portfolio 5) and a short position in the low momentum sub-portfolio (portfolio 1)
LS.Portfolio = XSMOM.output$returns[,5] + (-1*XSMOM.output$returns[,1])
# Investigate risk and return
table.AnnualizedReturns(LS.Portfolio,scale = 365, geometric = FALSE)

4.2 Double Sort with Lagged Returns and Volume

Following the methodology of @gargano2017value and @dickerson2018value we will use both the conditional and unconditional sorting functions to construct double sorted cryptocurrency portfolios based on past returns and trading volumes.