alvinalexander.com | career | drupal | java | mac | mysql | perl | scala | uml | unix  

Java example source code file (Position.java)

This example Java source code file (Position.java) is included in the alvinalexander.com "Java Source Code Warehouse" project. The intent of this project is to help you "Learn Java by Example" TM.

Learn more about this Java project at its project page.

Java - Java tags/keywords

bitset, firstcolumn, firstline, illegalargumentexception, indexoutofboundsexception, linemapimpl, lineshift, linetabmapimpl, maxcolumn, maxline, maxpos, nopos, position, tabinc, util

The Position.java Java example source code

/*
 * Copyright (c) 1999, 2012, Oracle and/or its affiliates. All rights reserved.
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
 *
 * This code is free software; you can redistribute it and/or modify it
 * under the terms of the GNU General Public License version 2 only, as
 * published by the Free Software Foundation.  Oracle designates this
 * particular file as subject to the "Classpath" exception as provided
 * by Oracle in the LICENSE file that accompanied this code.
 *
 * This code 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 General Public License
 * version 2 for more details (a copy is included in the LICENSE file that
 * accompanied this code).
 *
 * You should have received a copy of the GNU General Public License version
 * 2 along with this work; if not, write to the Free Software Foundation,
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 *
 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 * or visit www.oracle.com if you need additional information or have any
 * questions.
 */

package com.sun.tools.javac.util;

import java.util.BitSet;
import static com.sun.tools.javac.util.LayoutCharacters.*;

/** A class that defines source code positions as simple character
 *  offsets from the beginning of the file. The first character
 *  is at position 0.
 *
 *  Support is also provided for (line,column) coordinates, but tab
 *  expansion is optional and no Unicode excape translation is considered.
 *  The first character is at location (1,1).
 *
 *  <p>This is NOT part of any supported API.
 *  If you write code that depends on this, you do so at your own risk.
 *  This code and its internal interfaces are subject to change or
 *  deletion without notice.</b>
 */
public class Position {
    public static final int NOPOS        = -1;

    public static final int FIRSTPOS     = 0;
    public static final int FIRSTLINE    = 1;
    public static final int FIRSTCOLUMN  = 1;

    public static final int LINESHIFT    = 10;
    public static final int MAXCOLUMN    = (1< MAXCOLUMN) {
            return NOPOS;
        }
        return (line << LINESHIFT) + col;
    }

    public static interface LineMap extends com.sun.source.tree.LineMap {
        /** Find the start position of a line.
         *
         * @param line number of line (first is 1)
         * @return     position of first character in line
         * @throws  ArrayIndexOutOfBoundsException
         *           if {@code lineNumber < 1}
         *           if {@code lineNumber > no. of lines}
         */
        int getStartPosition(int line);

        /** Find the position corresponding to a (line,column).
         *
         * @param   line    number of line (first is 1)
         * @param   column  number of character on line (first is 1)
         *
         * @return  position of character
         * @throws  ArrayIndexOutOfBoundsException
         *           if {@code line < 1}
         *           if {@code line > no. of lines}
         */
        int getPosition(int line, int column);

        /** Find the line containing a position; a line termination
         * character is on the line it terminates.
         *
         * @param   pos  character offset of the position
         * @return the line number on which pos occurs (first line is 1)
         */
        int getLineNumber(int pos);

        /** Find the column for a character position.
         *  Note:  this method does not handle tab expansion.
         *  If tab expansion is needed, use a LineTabMap instead.
         *
         * @param  pos   character offset of the position
         * @return       the column number at which pos occurs
         */
        int getColumnNumber(int pos);
    }

    static class LineMapImpl implements LineMap {
        protected int[] startPosition; // start position of each line

        protected LineMapImpl() {}

        protected void build(char[] src, int max) {
            int c = 0;
            int i = 0;
            int[] linebuf = new int[max];
            while (i < max) {
                linebuf[c++] = i;
                do {
                    char ch = src[i];
                    if (ch == '\r' || ch == '\n') {
                        if (ch == '\r' && (i+1) < max && src[i+1] == '\n')
                            i += 2;
                        else
                            ++i;
                        break;
                    }
                    else if (ch == '\t')
                        setTabPosition(i);
                } while (++i < max);
            }
            this.startPosition = new int[c];
            System.arraycopy(linebuf, 0, startPosition, 0, c);
        }

        public int getStartPosition(int line) {
            return startPosition[line - FIRSTLINE];
        }

        public long getStartPosition(long line) {
            return getStartPosition(longToInt(line));
        }

        public int getPosition(int line, int column) {
            return startPosition[line - FIRSTLINE] + column - FIRSTCOLUMN;
        }

        public long getPosition(long line, long column) {
            return getPosition(longToInt(line), longToInt(column));
        }

        // Cache of last line number lookup
        private int lastPosition = Position.FIRSTPOS;
        private int lastLine = Position.FIRSTLINE;

        public int getLineNumber(int pos) {
            if (pos == lastPosition) {
                return lastLine;
            }
            lastPosition = pos;

            int low = 0;
            int high = startPosition.length-1;
            while (low <= high) {
                int mid = (low + high) >> 1;
                int midVal = startPosition[mid];

                if (midVal < pos)
                    low = mid + 1;
                else if (midVal > pos)
                    high = mid - 1;
                else {
                    lastLine = mid + 1; // pos is at beginning of this line
                    return lastLine;
                }
            }
            lastLine = low;
            return lastLine;  // pos is on this line
        }

        public long getLineNumber(long pos) {
            return getLineNumber(longToInt(pos));
        }

        public int getColumnNumber(int pos) {
            return pos - startPosition[getLineNumber(pos) - FIRSTLINE] + FIRSTCOLUMN;
        }

        public long getColumnNumber(long pos) {
            return getColumnNumber(longToInt(pos));
        }

        private static int longToInt(long longValue) {
            int intValue = (int)longValue;
            if (intValue != longValue)
                throw new IndexOutOfBoundsException();
            return intValue;
        }

        protected void setTabPosition(int offset) {}
    }

    /**
     * A LineMap that handles tab expansion correctly.  The cost is
     * an additional bit per character in the source array.
     */
    public static class LineTabMapImpl extends LineMapImpl {
        private BitSet tabMap;       // bits set for tab positions.

        public LineTabMapImpl(int max) {
            super();
            tabMap = new BitSet(max);
        }

        protected void setTabPosition(int offset) {
            tabMap.set(offset);
        }

        public int getColumnNumber(int pos) {
            int lineStart = startPosition[getLineNumber(pos) - FIRSTLINE];
            int column = 0;
            for (int bp = lineStart; bp < pos; bp++) {
                if (tabMap.get(bp))
                    column = (column / TabInc * TabInc) + TabInc;
                else
                    column++;
            }
            return column + FIRSTCOLUMN;
        }

        public int getPosition(int line, int column) {
            int pos = startPosition[line - FIRSTLINE];
            column -= FIRSTCOLUMN;
            int col = 0;
            while (col < column) {
                pos++;
                if (tabMap.get(pos))
                    col = (col / TabInc * TabInc) + TabInc;
                else
                    col++;
            }
            return pos;
        }
    }
}

Other Java examples (source code examples)

Here is a short list of links related to this Java Position.java source code file:

... this post is sponsored by my books ...

#1 New Release!

FP Best Seller

 

new blog posts

 

Copyright 1998-2021 Alvin Alexander, alvinalexander.com
All Rights Reserved.

A percentage of advertising revenue from
pages under the /java/jwarehouse URI on this website is
paid back to open source projects.