All Downloads are FREE. Search and download functionalities are using the official Maven repository.

de.ibapl.spsw.api.PortnamesComparator Maven / Gradle / Ivy

The newest version!
/*
 * SPSW - Drivers for the serial port, https://github.com/aploese/spsw/
 * Copyright (C) 2009-2021, Arne Plöse and individual contributors as indicated
 * by the @authors tag. See the copyright.txt in the distribution for a
 * full listing of individual contributors.
 *
 * This is free software; you can redistribute it and/or modify it
 * under the terms of the GNU Lesser General Public License as
 * published by the Free Software Foundation; either version 3 of
 * the License, or (at your option) any later version.
 *
 * This software is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this software; if not, write to the Free
 * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
 * 02110-1301 USA, or see the FSF site: http://www.fsf.org.
 */
package de.ibapl.spsw.api;

import java.io.Serializable;
import java.util.Comparator;

/**
 * Compare two port names so that COM1,COM2,COM10 are sorted in that order. The
 * natural order would be COM1,COM10,COM2, this might not be desired from the
 * users point of view. Shorter numbers are virtually filled up with leading
 * zeros and then they will be compared. The current implementation may be
 * changed if needed.
 *
 * "ttyUSB09".compareTo("ttyUSB19") == PortnamesComparator.compare("ttyUSB9",
 * "ttyUSB19")
 *
 * @author Arne Plöse
 *
 */
public class PortnamesComparator implements Comparator, Serializable {

    private final static long serialVersionUID = 1L;

    static class Iterator {

        final String value;
        final int length;
        int pos;
        int stuffedZeros;
        int zerosToFeed;

        public Iterator(String value) {
            this.value = value;
            this.length = value.length();
        }

        /**
         *
         * @return the number of digits from this pos
         */
        public int getNumberOfDigits() {
            int result = 0;
            while (Character.isDigit(value.charAt(pos + result))) {
                result++;
                if (pos + result == length) {
                    break;
                }
            }
            return result;
        }

        public void addZeros(int zerosToFeed) {
            this.zerosToFeed = zerosToFeed;
            this.stuffedZeros += zerosToFeed;
        }

        public char getChar() {
            if (zerosToFeed > 0) {
                return '0';
            } else {
                return value.charAt(pos);
            }
        }

        public boolean next() {
            if (zerosToFeed > 0) {
                zerosToFeed--;
            } else {
                pos++;
            }
            return pos < length;
        }

        public int overallLength() {
            return length + stuffedZeros;
        }

    }

    @Override
    public int compare(String valueA, String valueB) {
        Iterator iterA = new Iterator(valueA);
        Iterator iterB = new Iterator(valueB);
        int fisttStuffedAt = 0;
        int digitsFound = 0;
        while (iterA.next() && iterB.next()) {
            if (digitsFound == 0) {
                int digitsA = iterA.getNumberOfDigits();
                int digitsB = iterB.getNumberOfDigits();
                if (digitsA == digitsB) {

                } else {
                    if (fisttStuffedAt == 0) {
                        fisttStuffedAt = digitsA - digitsB;
                    }
                    if (digitsA > digitsB) {
                        iterB.addZeros(digitsA - digitsB);
                        digitsFound = digitsA;
                    } else if (digitsA < digitsB) {
                        iterA.addZeros(digitsB - digitsA);
                        digitsFound = digitsB;
                    }
                }
            } else {
                digitsFound--;
            }

            if (iterA.getChar() != iterB.getChar()) {
                return iterA.getChar() - iterB.getChar();
            }
        }
        int lengthDifference = iterA.overallLength() - iterB.overallLength();
        if (lengthDifference == 0) {
            return fisttStuffedAt;
        } else {
            return lengthDifference;
        }
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy