Вы ищете синтаксис from
(введен в Python 3), который позволяет обернуть исключение для конкретного приложения вокруг базового исключения. Вот пример:
>>> try:
... 1 > '1'
... except TypeError as e:
... raise AssertionError() from e
...
Traceback (most recent call last):
File "", line 2, in
TypeError: '>' not supported between instances of 'int' and 'str'
The above exception was the direct cause of the following exception:
Traceback (most recent call last):
File "", line 4, in
AssertionError
Вы можете указать строку, содержащую диагностическое сообщение, когда вы создаете новое исключение. Было бы лучше определить свои собственные исключения для конкретного приложения, а не перерабатывать AssertionError. Если вы определите несколько, сделайте одного из них [grand] родительским, а другие исключения наследуются от этого предка. Это позволяет вызывающим абонентам удобно ловить мелкие или грубые классы ошибок.
Существует PEP , который описывает дальнейшие соображения.
Маркируйте строки с точкой как разделитель и затем сравните целочисленный перевод рядом, начав слева.
Используя поток Java 8 для замены продвижения обнуляет в компонентах. Этот код прошел все тесты на interviewbit.com
public int compareVersion(String A, String B) {
List<String> strList1 = Arrays.stream(A.split("\\."))
.map(s -> s.replaceAll("^0+(?!$)", ""))
.collect(Collectors.toList());
List<String> strList2 = Arrays.stream(B.split("\\."))
.map(s -> s.replaceAll("^0+(?!$)", ""))
.collect(Collectors.toList());
int len1 = strList1.size();
int len2 = strList2.size();
int i = 0;
while(i < len1 && i < len2){
if (strList1.get(i).length() > strList2.get(i).length()) return 1;
if (strList1.get(i).length() < strList2.get(i).length()) return -1;
int result = new Long(strList1.get(i)).compareTo(new Long(strList2.get(i)));
if (result != 0) return result;
i++;
}
while (i < len1){
if (!strList1.get(i++).equals("0")) return 1;
}
while (i < len2){
if (!strList2.get(i++).equals("0")) return -1;
}
return 0;
}
Я записал небольшую библиотеку Java/Android для сравнения номеров версий: https://github.com/G00fY2/version-compare
, Что это в основном делает, является этим:
public int compareVersions(String versionA, String versionB) {
String[] versionTokensA = versionA.split("\\.");
String[] versionTokensB = versionB.split("\\.");
List<Integer> versionNumbersA = new ArrayList<>();
List<Integer> versionNumbersB = new ArrayList<>();
for (String versionToken : versionTokensA) {
versionNumbersA.add(Integer.parseInt(versionToken));
}
for (String versionToken : versionTokensB) {
versionNumbersB.add(Integer.parseInt(versionToken));
}
final int versionASize = versionNumbersA.size();
final int versionBSize = versionNumbersB.size();
int maxSize = Math.max(versionASize, versionBSize);
for (int i = 0; i < maxSize; i++) {
if ((i < versionASize ? versionNumbersA.get(i) : 0) > (i < versionBSize ? versionNumbersB.get(i) : 0)) {
return 1;
} else if ((i < versionASize ? versionNumbersA.get(i) : 0) < (i < versionBSize ? versionNumbersB.get(i) : 0)) {
return -1;
}
}
return 0;
}
Этот отрывок не предлагает проверок на ошибки или обработки. Около той моей библиотеки также поддерживает суффиксы как "с 1.2 дистанционными управлениями"> "с 1.2 бетами".
Вы нужно нормализовать строки версий, чтобы их можно было сравнивать. Что-то вроде
import java.util.regex.Pattern;
public class Main {
public static void main(String... args) {
compare("1.0", "1.1");
compare("1.0.1", "1.1");
compare("1.9", "1.10");
compare("1.a", "1.9");
}
private static void compare(String v1, String v2) {
String s1 = normalisedVersion(v1);
String s2 = normalisedVersion(v2);
int cmp = s1.compareTo(s2);
String cmpStr = cmp < 0 ? "<" : cmp > 0 ? ">" : "==";
System.out.printf("'%s' %s '%s'%n", v1, cmpStr, v2);
}
public static String normalisedVersion(String version) {
return normalisedVersion(version, ".", 4);
}
public static String normalisedVersion(String version, String sep, int maxWidth) {
String[] split = Pattern.compile(sep, Pattern.LITERAL).split(version);
StringBuilder sb = new StringBuilder();
for (String s : split) {
sb.append(String.format("%" + maxWidth + 's', s));
}
return sb.toString();
}
}
Prints
'1.0' <'1.1' '1.0.1' <'1.1' «1,9» <«1,10» '1.a'> '1.9'
public int compare(String v1, String v2) {
v1 = v1.replaceAll("\\s", "");
v2 = v2.replaceAll("\\s", "");
String[] a1 = v1.split("\\.");
String[] a2 = v2.split("\\.");
List<String> l1 = Arrays.asList(a1);
List<String> l2 = Arrays.asList(a2);
int i=0;
while(true){
Double d1 = null;
Double d2 = null;
try{
d1 = Double.parseDouble(l1.get(i));
}catch(IndexOutOfBoundsException e){
}
try{
d2 = Double.parseDouble(l2.get(i));
}catch(IndexOutOfBoundsException e){
}
if (d1 != null && d2 != null) {
if (d1.doubleValue() > d2.doubleValue()) {
return 1;
} else if (d1.doubleValue() < d2.doubleValue()) {
return -1;
}
} else if (d2 == null && d1 != null) {
if (d1.doubleValue() > 0) {
return 1;
}
} else if (d1 == null && d2 != null) {
if (d2.doubleValue() > 0) {
return -1;
}
} else {
break;
}
i++;
}
return 0;
}
]