No hay una respuesta sencilla. Si el tipo más grande en su máquina es largo y los dos tipos pasados son largos sin firmar y largos, ¿qué tipo esperaría que fuera val? Si no está firmado, corre el riesgo de un número negativo que no cabe en él. Si está firmado, puede desbordarse, pero aún así tener un número que encajaría en el espacio de número sin firmar.
Si estas limitaciones son aceptables, podría utilizar el enfoque de Alexey Malistov, pero el tipo resultante si Tipo1 y Tipo2 son del mismo tamaño, pero los diferentes tipos serán diferentes según el orden en que se pasen los valores.
Eche un vistazo a la función boost mpl if_, con la que puede elegir uno de dos tipos. Tendrá que idear sus propias reglas sobre cómo elegir el tipo resultante.
Relacionados: http://stackoverflow.com/questions/357629/how-do-you-find-the-range-of-values-that-integer-types-can-represent-in-c –
También puede utilice la plantilla 'uac_type' de esta solución: http://stackoverflow.com/questions/998571/c-template-for-safe-integer-casts/998982#998982. Pase los diferentes tipos y obtenga el tipo de resultado que el compilador elegiría. –