function calculate_pattern(parts, i)
    local under_pointer = 0
    for p = 1, #parts[i] do
        while under_pointer + 1 <= #parts[i+1] and parts[i+1][under_pointer+1].size > parts[i][p].size do
            under_pointer = under_pointer + 1
        end
        if under_pointer > 0 then
            parts[i][p].pattern = pattern_sum(parts, i+1, under_pointer)
        else
            parts[i][p].pattern = 0
        end
    end
end

pattern_sum = nil
do
    local memo = {}
    for i = 1, 3 do
        table.insert(memo, {})
    end
    function pattern_sum(parts, i, p_max)
        if memo[i][p_max] then
            return memo[i][p_max]
        end
        
        local sum = 0
        for p = 1, p_max do
            sum = sum + parts[i][p].pattern
        end
        memo[i][p_max] = sum
        return sum
    end
end

function main()
    local inputs = {}
    for i = 1, 4 do
        table.insert(inputs, io.read())
    end
    
    local n = tonumber(inputs[1])
    local parts = {}
    for i = 1, 3 do
        table.insert(parts, {})
        for size in inputs[1+i]:gmatch("%d+") do
            table.insert(parts[i], {size = tonumber(size), pattern = 1})
        end
    end
    
    for i = 1, #parts do
        table.sort(parts[i], function(a, b) return b.size < a.size end)
    end
    
    for i = #parts - 1, 1, -1 do
        calculate_pattern(parts, i)
    end
    
    print(pattern_sum(parts, 1, #parts[1]))
end

main()