find all paths between two vertices using SQL in OrientDB - orientdb

I have a simple scenario,
I want to select all the path between Adrian and Permies,
The shortestPath function gives me
Adrian -> Permies
but I cannot get the other path which is,
Adrian -> Devs -> Permies

With Java, you could use the following code and the following class
OrientGraph g=new OrientGraph(currentPath);
AllPaths allPath = new AllPaths(g);
List<List<Vertex>> paths=allPath.getPaths("#11:0","#11:7");
Class AllPaths
import java.util.ArrayList;
import java.util.List;
import com.tinkerpop.blueprints.Direction;
import com.tinkerpop.blueprints.Vertex;
import com.tinkerpop.blueprints.impls.orient.OrientGraph;
public class AllPaths {
private boolean stop=false;
private Vertex vertexFrom=null;
private List<Vertex> vertexPreviousStep=new ArrayList<Vertex>();
private List<Vertex> vertexCurrently=new ArrayList<Vertex>();
private List<List<Vertex>> paths=new ArrayList<List<Vertex>>();
private OrientGraph g;
public AllPaths(OrientGraph g) {
this.g=g;
}
protected List<List<Vertex>> getPaths(String ridFrom, String ridTo) {
if(!check(ridFrom,ridTo))
return paths;
vertexPreviousStep.add(vertexFrom);
List<Vertex> p=new ArrayList<Vertex>();
p.add(vertexFrom);
paths.add(p);
int step=1;
do{
stop=false;
for(Vertex v: vertexPreviousStep){
List<Vertex> toAdd=new ArrayList<Vertex>();
Iterable<Vertex> nodes = (Iterable<Vertex>) v.getVertices(Direction.OUT);
for(Vertex v1:nodes){
toAdd.add(v1);
if(!v1.getId().toString().equals(ridTo))
vertexCurrently.add(v1);
}
if(toAdd.size()!=0)
setPaths(v,toAdd,step);
}
change();
step++;
}while(stop==true);
return cleanPaths(ridTo);
}
private boolean check(String ridFrom,String ridTo) {
boolean findFrom=false,findTo=false;
for(Vertex v:g.getVertices()){
if(v.getId().toString().equals(ridFrom)){
findFrom=true;
vertexFrom=v;
}
else if(v.getId().toString().equals(ridTo))
findTo=true;
}
if(findFrom==false || findTo==false)
return false;
return true;
}
public void change(){
vertexPreviousStep.clear();
for(Vertex v:vertexCurrently)
vertexPreviousStep.add(v);
vertexCurrently.clear();
}
private void setPaths(Vertex previousVertex,List<Vertex> toAdd,int step) {
for(int i=0;i<paths.size();i++){
List<Vertex> list=paths.get(i);
Vertex last=list.get(list.size()-1);
if(last.getId().toString().equals(previousVertex.getId().toString()) && list.size()==step){
int j=0;
for(Vertex v1:toAdd){
boolean vertexFound=false;
for(Vertex v2:list){
if(v2.getId().toString().equals(v1.getId().toString()))
vertexFound=true;
}
if(vertexFound==false){
List<Vertex> listVertex=new ArrayList<Vertex>();
for(Vertex p:list)
listVertex.add(p);
listVertex.add(v1);
if(j==0){
stop=true;
paths.set(i,listVertex);
j++;
}
else
paths.add(listVertex);
}
}
}
}
}
public List<List<Vertex>> cleanPaths(String ridTo){
for(int i=0;i<paths.size();i++){
List<Vertex> list=paths.get(i);
if(!list.get(list.size()-1).getId().toString().equals(ridTo)){
paths.remove(i);
i--;
}
}
return paths;
}
}

Well, I gonna share 2 ways:
a) using traverse but specifying the deep:
TRAVERSE * FROM (SELECT FROM Source WHERE field = 'value') MAXDEPTH 3
b) using some constraint clause:
SELECT FROM (TRAVERSE * FROM (SELECT FROM Source WHERE field = 'value') while #rid <> (SELECT FROM Target WHERE field='value'))

Related

Could someone give me an example of how to extract coordinates for a 'word' using PDFBox

Could someone give me an example of how to extract coordinates for a 'word' with PDFBox
I am using this link to extract positions of individual characters:
https://www.tutorialkart.com/pdfbox/how-to-extract-coordinates-or-position-of-characters-in-pdf/
I am using this link to extract words:
https://www.tutorialkart.com/pdfbox/extract-words-from-pdf-document/
I am stuck getting coordinates for whole words.
You can extract the coordinates of words by collecting all the TextPosition objects building a word and combining their bounding boxes.
Implementing this along the lines of the two tutorials you referenced, you can extend PDFTextStripper like this:
public class GetWordLocationAndSize extends PDFTextStripper {
public GetWordLocationAndSize() throws IOException {
}
#Override
protected void writeString(String string, List<TextPosition> textPositions) throws IOException {
String wordSeparator = getWordSeparator();
List<TextPosition> word = new ArrayList<>();
for (TextPosition text : textPositions) {
String thisChar = text.getUnicode();
if (thisChar != null) {
if (thisChar.length() >= 1) {
if (!thisChar.equals(wordSeparator)) {
word.add(text);
} else if (!word.isEmpty()) {
printWord(word);
word.clear();
}
}
}
}
if (!word.isEmpty()) {
printWord(word);
word.clear();
}
}
void printWord(List<TextPosition> word) {
Rectangle2D boundingBox = null;
StringBuilder builder = new StringBuilder();
for (TextPosition text : word) {
Rectangle2D box = new Rectangle2D.Float(text.getXDirAdj(), text.getYDirAdj(), text.getWidthDirAdj(), text.getHeightDir());
if (boundingBox == null)
boundingBox = box;
else
boundingBox.add(box);
builder.append(text.getUnicode());
}
System.out.println(builder.toString() + " [(X=" + boundingBox.getX() + ",Y=" + boundingBox.getY()
+ ") height=" + boundingBox.getHeight() + " width=" + boundingBox.getWidth() + "]");
}
}
(ExtractWordCoordinates inner class)
and run it like this:
PDDocument document = PDDocument.load(resource);
PDFTextStripper stripper = new GetWordLocationAndSize();
stripper.setSortByPosition( true );
stripper.setStartPage( 0 );
stripper.setEndPage( document.getNumberOfPages() );
Writer dummy = new OutputStreamWriter(new ByteArrayOutputStream());
stripper.writeText(document, dummy);
(ExtractWordCoordinates test testExtractWordsForGoodJuJu)
Applied to the apache.pdf example the tutorials use you get:
2017-8-6 [(X=26.004425048828125,Y=22.00372314453125) height=5.833024024963379 width=36.31868362426758]
Welcome [(X=226.44479370117188,Y=22.00372314453125) height=5.833024024963379 width=36.5999755859375]
to [(X=265.5881652832031,Y=22.00372314453125) height=5.833024024963379 width=8.032623291015625]
The [(X=276.1641845703125,Y=22.00372314453125) height=5.833024024963379 width=14.881439208984375]
Apache [(X=293.5890197753906,Y=22.00372314453125) height=5.833024024963379 width=29.848846435546875]
Software [(X=325.98126220703125,Y=22.00372314453125) height=5.833024024963379 width=35.271636962890625]
Foundation! [(X=363.7962951660156,Y=22.00372314453125) height=5.833024024963379 width=47.871429443359375]
Custom [(X=334.0334777832031,Y=157.6195068359375) height=4.546705722808838 width=25.03936767578125]
Search [(X=360.8929138183594,Y=157.6195068359375) height=4.546705722808838 width=22.702728271484375]
You can create CustomPDFTextStripper which extends PDFTextStripper and override protected void writeString(String text, List<TextPosition> textPositions). In this overriden method you need to split textPositions by the word separator to get List<TextPosition> for each word. After that you can join each character and compute bounding box.
Full example below which contains also drawing of the resulting bounding boxes.
package com.example;
import lombok.Value;
import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.rendering.PDFRenderer;
import org.apache.pdfbox.text.PDFTextStripper;
import org.apache.pdfbox.text.TextPosition;
import org.junit.Ignore;
import org.junit.Test;
import javax.imageio.ImageIO;
import java.awt.*;
import java.awt.image.BufferedImage;
import java.io.*;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;
public class PdfBoxTest {
private static final String BASE_DIR_PATH = "C:\\Users\\Milan\\50330484";
private static final String INPUT_FILE_PATH = "input.pdf";
private static final String OUTPUT_IMAGE_PATH = "output.jpg";
private static final String OUTPUT_BBOX_IMAGE_PATH = "output-bbox.jpg";
private static final float FROM_72_TO_300_DPI = 300.0f / 72.0f;
#Test
public void run() throws Exception {
pdfToImage();
drawBoundingBoxes();
}
#Ignore
#Test
public void pdfToImage() throws IOException {
PDDocument document = PDDocument.load(new File(BASE_DIR_PATH, INPUT_FILE_PATH));
PDFRenderer renderer = new PDFRenderer(document);
BufferedImage image = renderer.renderImageWithDPI(0, 300);
ImageIO.write(image, "JPEG", new File(BASE_DIR_PATH, OUTPUT_IMAGE_PATH));
}
#Ignore
#Test
public void drawBoundingBoxes() throws IOException {
PDDocument document = PDDocument.load(new File(BASE_DIR_PATH, INPUT_FILE_PATH));
List<WordWithBBox> words = getWords(document);
draw(words);
}
private List<WordWithBBox> getWords(PDDocument document) throws IOException {
CustomPDFTextStripper customPDFTextStripper = new CustomPDFTextStripper();
customPDFTextStripper.setSortByPosition(true);
customPDFTextStripper.setStartPage(0);
customPDFTextStripper.setEndPage(1);
Writer writer = new OutputStreamWriter(new ByteArrayOutputStream());
customPDFTextStripper.writeText(document, writer);
List<WordWithBBox> words = customPDFTextStripper.getWords();
return words;
}
private void draw(List<WordWithBBox> words) throws IOException {
BufferedImage bufferedImage = ImageIO.read(new File(BASE_DIR_PATH, OUTPUT_IMAGE_PATH));
Graphics2D graphics = bufferedImage.createGraphics();
graphics.setColor(Color.GREEN);
List<Rectangle> rectangles = words.stream()
.map(word -> new Rectangle(word.getX(), word.getY(), word.getWidth(), word.getHeight()))
.collect(Collectors.toList());
rectangles.forEach(graphics::draw);
graphics.dispose();
ImageIO.write(bufferedImage, "JPEG", new File(BASE_DIR_PATH, OUTPUT_BBOX_IMAGE_PATH));
}
private class CustomPDFTextStripper extends PDFTextStripper {
private final List<WordWithBBox> words;
public CustomPDFTextStripper() throws IOException {
this.words = new ArrayList<>();
}
public List<WordWithBBox> getWords() {
return new ArrayList<>(words);
}
#Override
protected void writeString(String text, List<TextPosition> textPositions) throws IOException {
String wordSeparator = getWordSeparator();
List<TextPosition> wordTextPositions = new ArrayList<>();
for (TextPosition textPosition : textPositions) {
String str = textPosition.getUnicode();
if (wordSeparator.equals(str)) {
if (!wordTextPositions.isEmpty()) {
this.words.add(createWord(wordTextPositions));
wordTextPositions.clear();
}
} else {
wordTextPositions.add(textPosition);
}
}
super.writeString(text, textPositions);
}
private WordWithBBox createWord(List<TextPosition> wordTextPositions) {
String word = wordTextPositions.stream()
.map(TextPosition::getUnicode)
.collect(Collectors.joining());
int minX = Integer.MAX_VALUE;
int minY = Integer.MAX_VALUE;
int maxX = Integer.MIN_VALUE;
int maxY = Integer.MIN_VALUE;
for (TextPosition wordTextPosition : wordTextPositions) {
minX = Math.min(minX, from72To300Dpi(wordTextPosition.getXDirAdj()));
minY = Math.min(minY, from72To300Dpi(wordTextPosition.getYDirAdj() - wordTextPosition.getHeightDir()));
maxX = Math.max(maxX, from72To300Dpi(wordTextPosition.getXDirAdj() + wordTextPosition.getWidthDirAdj()));
maxY = Math.max(maxY, from72To300Dpi(wordTextPosition.getYDirAdj()));
}
return new WordWithBBox(word, minX, minY, maxX - minX, maxY - minY);
}
}
private int from72To300Dpi(float f) {
return Math.round(f * FROM_72_TO_300_DPI);
}
#Value
private class WordWithBBox {
private final String word;
private final int x;
private final int y;
private final int width;
private final int height;
}
}
Note:
If you are interested in other options, you can check also Poppler
PDF to image
pdftoppm -r 300 -jpeg input.pdf output
Generate an XHTML file containing bounding box information for each word in the file.
pdftotext -r 300 -bbox input.pdf

How select random documents in OrientDB

I write online game. For game logic, I need select random users(etc) from database. How to achive this with java api? What the most perfomance way to do this?
I can use something like(pseudocode): select from User skip(randomNum(0,usersCount)) limit 1 but how write in documentation - skip has bad performance.
I have tried with this code
int numberRandom= 5;
String string="[";
int cluster= db.getMetadata().getSchema().getClass("User").getClusterIds()[0];
for(int i=0;i<numberRandom;i++){
int random=ThreadLocalRandom.current().nextInt(0, 96000);
if(i==(numberRandom-1))
string += cluster+":"+random + "]";
else
string += cluster+":"+random + ",";
}
Iterable<Vertex> result = g.command(new OCommandSQL("select from "+ string)).execute();
for(Vertex v:result)
System.out.println(v.getId());
Let me know if it can be a good solution for you
I wrote two java classes, both are getting X random users from a specific cluster.
The first one seams faster to me. (about 0.8s vs 1.2s)
testRandom.java
public class testRandom {
public static void main(String[] args) {
// TODO Auto-generated method stub
String nomeDb = "RandomUser";
try {
OServerAdmin serverAdmin = new OServerAdmin("remote:localhost/"+nomeDb).connect("root", "root");
if(serverAdmin.existsDatabase()){ // il db esiste
//connessione a db
OrientGraph g = new OrientGraph("remote:localhost/"+nomeDb);
//------------------------------------------------
long Tbegin,Tend;
float millis;
Tbegin = System.currentTimeMillis();
int numberRandom= 5;
int random;
String cluster = "user";
Iterable<Vertex> vertices = g.command(new OCommandSQL("select from cluster:"+cluster)).execute();
List<Vertex> v_array = new ArrayList<Vertex>();
List<Vertex> res = new ArrayList<Vertex>();
for(Vertex v : vertices){
v_array.add(v);
}
int arraysize = v_array.size();
for(int i=0;i<numberRandom;i++){
random=ThreadLocalRandom.current().nextInt(0, arraysize);
res.add(v_array.get(random));
}
for(Vertex v : res){
System.out.println(v.getId());
}
Tend = System.currentTimeMillis();
millis = (Tend-Tbegin);
System.out.println("--Execution time: "+millis/1000+ "s\n");
//------------------------------------------------
//chiude db
g.shutdown();
}
else{
System.out.println("Il database '"+ nomeDb + "' non esiste");
}
serverAdmin.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
testRandomSkip.java
public class testRandom_skip {
public static void main(String[] args) {
// TODO Auto-generated method stub
String nomeDb = "RandomUser";
try {
OServerAdmin serverAdmin = new OServerAdmin("remote:localhost/"+nomeDb).connect("root", "root");
if(serverAdmin.existsDatabase()){ // il db esiste
//connessione a db
OrientGraph g = new OrientGraph("remote:localhost/"+nomeDb);
//------------------------------------------------
long Tbegin,Tend;
float millis;
Tbegin = System.currentTimeMillis();
int numberRandom= 5;
int random;
String cluster = "user";
List<Vertex> res = new ArrayList<Vertex>();
Iterable<Vertex> q_count_V = g.command(new OCommandSQL("select count(*) from cluster:"+cluster)).execute();
Long count_V = 0l;
for(Vertex v : q_count_V){
count_V=v.getProperty("count");
break;
}
for(int i=0;i<numberRandom;i++){
random=(int)ThreadLocalRandom.current().nextLong(0, count_V);
Iterable<Vertex> vertex = g.command(new OCommandSQL("select from cluster:"+cluster+" skip "+random+" limit 1")).execute();
for(Vertex v : vertex){
res.add(v);
break;
}
}
for(Vertex v : res){
System.out.println(v.getId());
}
Tend = System.currentTimeMillis();
millis = (Tend-Tbegin);
System.out.println("--Execution time: "+millis/1000+ "s\n");
//------------------------------------------------
//chiude db
g.shutdown();
}
else{
System.out.println("Il database '"+ nomeDb + "' non esiste");
}
serverAdmin.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
Hope it helps.
Ivan

How to query all paths in orientdb sql

I want to find all paths between two vertices. I was able to find it using gremlin path function but it too slow.
Equivalent Gremlin: g.v('12:0').both.both.has('idx', 1L).path
How to convert above gremlin to OrientDB SQL?
In OrientDB 2.1, there is (alas) no way to query for "all paths" using OSQL.
There are proposals for OSQL enhancements to support "all paths" functionality -- see in particular https://github.com/orientechnologies/orientdb/issues/4474 --
but apparently this is for 2.2 or beyond.
In the meantime, note that shortestPath(_) does allow one to specify an edge class, so it can potentially be used to explore alternative paths.
With Java, you could use the following code and the following class
OrientGraph g=new OrientGraph(currentPath);
AllPaths allPath = new AllPaths(g);
List<List<Vertex>> paths=allPath.getPaths("#11:0","#11:7");
Class AllPaths
import java.util.ArrayList;
import java.util.List;
import com.tinkerpop.blueprints.Direction;
import com.tinkerpop.blueprints.Vertex;
import com.tinkerpop.blueprints.impls.orient.OrientGraph;
public class AllPaths {
private boolean stop=false;
private Vertex vertexFrom=null;
private List<Vertex> vertexPreviousStep=new ArrayList<Vertex>();
private List<Vertex> vertexCurrently=new ArrayList<Vertex>();
private List<List<Vertex>> paths=new ArrayList<List<Vertex>>();
private OrientGraph g;
public AllPaths(OrientGraph g) {
this.g=g;
}
protected List<List<Vertex>> getPaths(String ridFrom, String ridTo) {
if(!check(ridFrom,ridTo))
return paths;
vertexPreviousStep.add(vertexFrom);
List<Vertex> p=new ArrayList<Vertex>();
p.add(vertexFrom);
paths.add(p);
int step=1;
do{
stop=false;
for(Vertex v: vertexPreviousStep){
List<Vertex> toAdd=new ArrayList<Vertex>();
Iterable<Vertex> nodes = (Iterable<Vertex>) v.getVertices(Direction.OUT);
for(Vertex v1:nodes){
toAdd.add(v1);
if(!v1.getId().toString().equals(ridTo))
vertexCurrently.add(v1);
}
if(toAdd.size()!=0)
setPaths(v,toAdd,step);
}
change();
step++;
}while(stop==true);
return cleanPaths(ridTo);
}
private boolean check(String ridFrom,String ridTo) {
boolean findFrom=false,findTo=false;
for(Vertex v:g.getVertices()){
if(v.getId().toString().equals(ridFrom)){
findFrom=true;
vertexFrom=v;
}
else if(v.getId().toString().equals(ridTo))
findTo=true;
}
if(findFrom==false || findTo==false)
return false;
return true;
}
public void change(){
vertexPreviousStep.clear();
for(Vertex v:vertexCurrently)
vertexPreviousStep.add(v);
vertexCurrently.clear();
}
private void setPaths(Vertex previousVertex,List<Vertex> toAdd,int step) {
for(int i=0;i<paths.size();i++){
List<Vertex> list=paths.get(i);
Vertex last=list.get(list.size()-1);
if(last.getId().toString().equals(previousVertex.getId().toString()) && list.size()==step){
int j=0;
for(Vertex v1:toAdd){
boolean vertexFound=false;
for(Vertex v2:list){
if(v2.getId().toString().equals(v1.getId().toString()))
vertexFound=true;
}
if(vertexFound==false){
List<Vertex> listVertex=new ArrayList<Vertex>();
for(Vertex p:list)
listVertex.add(p);
listVertex.add(v1);
if(j==0){
stop=true;
paths.set(i,listVertex);
j++;
}
else
paths.add(listVertex);
}
}
}
}
}
public List<List<Vertex>> cleanPaths(String ridTo){
for(int i=0;i<paths.size();i++){
List<Vertex> list=paths.get(i);
if(!list.get(list.size()-1).getId().toString().equals(ridTo)){
paths.remove(i);
i--;
}
}
return paths;
}
}
If you want I can write a javascript function

How to get the average of a generic array list in java?

i'm having trouble getting the average of a generic array list of type T.
You should use <T extends Number> generic signature to specify the type of the Number types, plus, you should use instanceof keyword. A simple dummy demo here;
Test Code
import java.util.ArrayList;
import java.util.List;
public class Test {
public static void main(String[] args) {
List<Integer> integerList = new ArrayList<Integer>();
List<Double> doubleList = new ArrayList<Double>();
List<Float> floatList = new ArrayList<Float>();
for(int i = 0; i < 10; i++)
{
integerList.add(new Integer(i+1));
doubleList.add(new Double(i+1));
floatList.add(new Float(i+1));
}
Utility<Integer> utilityInteger = new Utility<Integer>(integerList);
Utility<Double> utilityDouble = new Utility<Double>(doubleList);
Utility<Float> utilityFloat = new Utility<Float>(floatList);
System.out.println("Integer average: " + utilityInteger.getAverage());
System.out.println("Double average : " + utilityDouble.getAverage());
System.out.println("Float average : " + utilityFloat.getAverage());
}
public static class Utility<T extends Number>
{
// Fields
private List<T> list;
private Object average;
// Constructor
#SuppressWarnings("unchecked")
public Utility(List<T> list)
{
this.list = list;
T sample = list.get(0);
if(sample instanceof Double)
{
doAverageDouble((List<Double>) list);
}
else if (sample instanceof Integer)
{
doAverageInteger((List<Integer>) list);
}
else if (sample instanceof Float)
{
doAverageFloat((List<Float>) list);
}
else
{
throw new IllegalStateException("Constructor must be initialiez with either of Double, Integer or Float list");
}
}
// Methods
private void doAverageDouble(List<Double> list) {
Double sum = new Double(0);
for(Double d : list)
{
sum += d;
}
average = sum/new Double(list.size());
}
private void doAverageInteger(List<Integer> list) {
Integer sum = new Integer(0);
for(Integer d : list)
{
sum += d;
}
average = sum/new Integer(list.size());
}
private void doAverageFloat(List<Float> list) {
Float sum = new Float(0);
for(Float d : list)
{
sum += d;
}
average = sum/new Float(list.size());
}
Object getAverage()
{
return average;
}
}
}
Console Output
Integer average: 5
Double average : 5.5
Float average : 5.5

Why I get null.pointer exception, I am sure where aren't any null variables

public class Server {
public static Maze lab;
public static Socket s;
public static Socket z;
public static player human;
public static BufferedReader input;
public static OutputStream os;
public static InputStream is;
public static int n=-1;
public static connections info;
public static ObjectOutputStream oos;
public static void main(String[] args) {
try{
ServerSocket Serversocket = new ServerSocket(1900);
System.out.println("Maze Game Server Started on port " + Serversocket.getLocalPort());
FileInputStream fis = new FileInputStream("labirintas.cfg");
ObjectInputStream ois = new ObjectInputStream(fis);
lab = (Maze) ois.readObject();
fis.close();
ois.close();
info = new connections();
try {
while(true){
try{
s = Serversocket.accept();
z = Serversocket.accept();
System.out.println("Conection from: " + s.getLocalAddress().getHostAddress());
os = s.getOutputStream();
is = z.getInputStream();
oos = new ObjectOutputStream(os);
oos.writeObject(lab);
oos.flush();
n++;
//is.close();
human = new player(n);
human.start();
}catch(Exception exception){
System.out.println("nėra labirinto" + exception.getMessage());
System.exit(0);
}finally
{
s.close();
}
}
} catch ( Exception ex) {
System.out.println(ex.getMessage());
}
}catch(Exception e){
System.out.println(e.getMessage());
}
}
public static class player extends Thread{
public int x=0;
public int y=0;
public int counter = 0;
public String nick="";
public player(int n){
x=0;
y=0;
counter = n;
try{
input = new BufferedReader(new InputStreamReader(is));
nick = input.readLine();
System.out.println(counter+" "+x+" "+y+" "+ nick );
info.info(counter, x, y, nick);
oos.writeObject(info);
oos.flush();
}catch(Exception e){
System.out.println(e.getStackTrace());
}
}
public int getcooX(){
return x;
}
public int getcooY(){
return y;
}
public void moveUP(){
x--;
}
public void moveDOWN(){
x++;
}
public void moveLEFT(){
y--;
}
public void moveRIGHT(){
y++;
}
#Override
public void run(){
try{
while(true){
System.out.println(s + " with name: "+ nick + ": " + (s.isConnected()?"true":"false"));
if (input!=null){
String command = input.readLine();
System.out.println(command);
if(command.startsWith("MOVE_UP")){
System.out.println("up move");
if (lab.checkUP(x, y)==false){
System.out.println("up accepted");
x--;
info.info(counter, x, y, nick);
oos.writeObject(info);
oos.flush();
}
if(lab.isItWin(x, y)){
System.out.println("Winner");
s.close();
}
}
else if(command.startsWith("MOVE_LEFT")){
System.out.println("left move");
if (lab.checkLEFT(x, y)==false){
System.out.println("left accepted");
y--;
info.info(counter, x, y, nick);
oos.writeObject(info);
oos.flush();
}
if(lab.isItWin(x, y)){
System.out.println("Winner");
s.close();
}
}
else if(command.startsWith("MOVE_RIGHT")){
System.out.println("right move");
if (lab.checkRIGHT(x, y)==false){
System.out.println("right accepted");
y++;
info.info(counter, x, y, nick);
oos.writeObject(info);
oos.flush();
}
if(lab.isItWin(x, y)){
System.out.println("Winner");
s.close();
}
}
else if(command.startsWith("MOVE_DOWN")){
System.out.println("down move");
if (lab.checkRIGHT(x, y)==false){
System.out.println("down accepted");
y++;
info.info(counter, x, y, nick);
oos.writeObject(info);
oos.flush();
}
if(lab.isItWin(x, y)){
System.out.println("Winner");
s.close();
}
}
}
}
}catch(Exception e){
System.out.println(e.getMessage());
}
}
}
}
Why do I get java.lang.NullPointerException? I think I'm doing everything right. I don't understand why I get this.
here the client, and the connections classes.
public class Client implements ActionListener, Serializable{
public static JFrame main;
public static JPanel mainP;
public static JLabel text;
public static JButton New;
public static JButton exit;
public static JTextField nickas;
public JPanel labirintas;
public JMenuBar bar;
public JMenu file;
public JMenu edit;
public JMenuItem close;
public JFrame kurti;
public JLabel[][] label;
public JFrame zaidimas;
public static Maze lab;
public Color sienos = Color.BLACK;
public Color zaidejo = Color.RED;
public Color laimejimo = Color.GREEN;
public Color laukeliai = Color.WHITE;
public int cooX = 0;
public int cooY = 0;
public static PrintWriter output;
public static Socket s;
public static Socket f;
public static connections info;
public static InputStream os;
public static ObjectInputStream oos;
public static void main(String[] args) {
main = new JFrame("Pagrindinis meniu");
main.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
mainP = new JPanel();
text = new JLabel("Sveiki čia labirinto žaidimas. Įveskite savo vardą. Pasirinkite ką"
+ " darysite", SwingConstants.CENTER);
text.setVerticalAlignment(SwingConstants.TOP);
New = new JButton("Pradėti žaidimą");
nickas = new JTextField();
nickas.setDocument(new JTextFieldLimit(10));
mainP.setLayout(new GridBagLayout());
GridBagConstraints c = new GridBagConstraints();
c.fill = GridBagConstraints.HORIZONTAL;
c.gridx = 0;
c.gridy = 0;
c.insets = new Insets(10,0,0,0);
mainP.add(text, c);
c.gridx=0;
c.gridy = 1;
mainP.add(nickas, c);
c.gridx = 0;
c.gridy = 2;
mainP.add(New, c);
exit = new JButton("Išeiti iš žaidimo");
c.gridx = 0;
c.gridy = 3;
mainP.add(exit, c);
main.add(mainP);
main.setSize(500, 500);
main.show();
New.addActionListener(new Client());
exit.addActionListener(new Client());
}
#Override
public void actionPerformed(ActionEvent e){
Object source =e.getActionCommand();
if (source.equals("Pradėti žaidimą")){
String nick = nickas.getText();
try{
if(nick.isEmpty()){
JOptionPane.showMessageDialog(main, "Enter Your name", "Please Enter Your name", JOptionPane.ERROR_MESSAGE);
}
else{
s = new Socket("localhost",1900);
f = new Socket("localhost",1900);
os = s.getInputStream();
oos = new ObjectInputStream(os);
lab = (Maze) oos.readObject();
OutputStream is = f.getOutputStream();
//os.close();
output = new PrintWriter(is, true);
main.show(false);
zaidimas =new JFrame("Labirinto kurimas");//sukuriu nauja frame labirinto zaidimui
zaidimas.setLayout(new GridBagLayout());
zaidimas.setBackground(Color.BLACK);
GridBagConstraints ck = new GridBagConstraints(); //sukuriu nauja GridBagConstraints stiliui kurti
/////////////////////
zaidimas.setSize(1200, 600);
bar = new JMenuBar();//meniu juosta
file = new JMenu("File");
edit = new JMenu("Edit");
/////////////////////
bar.add(file);
bar.add(edit);
file.add(close = new JMenuItem("Close"));
close.setAccelerator(KeyStroke.getKeyStroke('C', Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));
//////////////////
JMenuItem spalvos = new JMenuItem("Spalvų meniu");
edit.add(spalvos);
spalvos.setAccelerator(KeyStroke.getKeyStroke('P', Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));
/////////////////
ck.gridx = 0;//pridedu ja i tokias koordinates
ck.gridy = 0;
ck.fill = GridBagConstraints.HORIZONTAL;//issitemptu horizontaliai
ck.anchor = GridBagConstraints.NORTHWEST;
ck.gridwidth = 4;
ck.weightx = 1.0;
ck.weighty = 0.0;
zaidimas.add(bar, ck);
/////////////////////
labirintas = new JPanel();//labirinto panele
labirintas.setLayout(new GridLayout(lab.h,lab.v));
ck.gridy = 1;
ck.weightx = 0.8;
ck.weighty = 1.0;
ck.fill = GridBagConstraints.BOTH;
zaidimas.add(labirintas, ck);
/////////////////////
text = new JLabel("Online:");
ck.gridx = 4;
ck.weightx = 0.2;
ck.weighty=1.0;
ck.fill = GridBagConstraints.BOTH;
ck.anchor = GridBagConstraints.FIRST_LINE_START;
zaidimas.add(text, ck);
////////
label = new JLabel[lab.h][lab.v];//sukuriu masyva labeliu
////////////////
sienos();
///////////////
label[0][0].setBackground(zaidejo);
///////////////
try{
output.println(nick);
online();
}catch(Exception b){
}
zaidimas.addKeyListener(new KeyListener(){
#Override
public void keyReleased(KeyEvent K){
try{
if (K.getKeyCode()==KeyEvent.VK_A){
output.println("MOVE_LEFT");
output.flush();
if (lab.checkLEFT(cooX, cooY)==false){
label[cooX][cooY].setBackground(Color.white);
cooY--;
online();
}
if(lab.isItWin(cooX, cooY)){
JOptionPane.showMessageDialog(main, "Winner!", "You Won.", JOptionPane.PLAIN_MESSAGE);
System.out.println("Winner");
s.close();
f.close();
System.exit(0);
}
}
else if (K.getKeyCode()==KeyEvent.VK_W){
output.println("MOVE_UP");
output.flush();
if (lab.checkUP(cooX, cooY)==false){
label[cooX][cooY].setBackground(Color.white);
cooX--;
online();
}
if(lab.isItWin(cooX, cooY)){
JOptionPane.showMessageDialog(main, "Winner!", "You Won.", JOptionPane.PLAIN_MESSAGE);
System.out.println("Winner");
s.close();
f.close();
System.exit(0);
}
}
else if (K.getKeyCode()==KeyEvent.VK_D){
output.println("MOVE_RIGHT");
output.flush();
if (lab.checkRIGHT(cooX, cooY)==false){
label[cooX][cooY].setBackground(Color.white);
cooY++;
online();
}
if(lab.isItWin(cooX, cooY)){
JOptionPane.showMessageDialog(main, "Winner!", "You Won.", JOptionPane.PLAIN_MESSAGE);
System.out.println("Winner");
s.close();
f.close();
System.exit(0);
}
}
if (K.getKeyCode()==KeyEvent.VK_S){
output.println("MOVE_DOWN");
output.flush();
if (lab.checkDOWN(cooX, cooY)==false){
label[cooX][cooY].setBackground(Color.white);
cooX++;
online();
}
if(lab.isItWin(cooX, cooY)){
JOptionPane.showMessageDialog(main, "Winner!", "You Won.", JOptionPane.PLAIN_MESSAGE);
System.out.println("Winner");
s.close();
f.close();
System.exit(0);
}
}
}catch(Exception ex){
}
}
public void keyPressed(KeyEvent key){}
public void keyTyped(KeyEvent keyE){}
});
///////////////
zaidimas.show();
close.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e){
zaidimas.dispose();
main.dispose();
System.exit(0);
}
});
zaidimas.addWindowListener(new WindowAdapter(){
#Override
public void windowClosing(WindowEvent wind){
main.show(true);
mainP.show(true);
try{
s.close();
f.close();
}catch(Exception ex){
}
}
});
}
}catch(UnknownHostException exception){
JOptionPane.showMessageDialog(main, exception.getMessage()+exception, "Host error", JOptionPane.ERROR_MESSAGE);
exception.getStackTrace();
}
catch(Exception except){
JOptionPane.showMessageDialog(main, except.getMessage()+except, "Fatal error", JOptionPane.ERROR_MESSAGE);
except.getStackTrace();
}
}
else if (source.equals("Išeiti iš žaidimo")){
main.dispose();
System.exit(0);
}
}
// public void gamer(){//tikrina ar zaidejas yra laimejimo langelija
// label[game.getcooX()][game.getcooY()].setBackground(zaidejo);
// if (lab.isItWin(game.getcooX(), game.getcooY())){
// zaidimas.dispose();
// JOptionPane.showMessageDialog(main, "Jūs laimėjote!", "Sveikiname", JOptionPane.ERROR_MESSAGE);
// main.show(true);
// mainP.show(true);
// }
// }
public void sienos(){
for(int i=0;i<lab.h;i++){
for(int j=0; j<lab.v;j++){//ciklas braizyti sienom
label[i][j] = new JLabel();
int t=0,r=0,bot=0,l = 0;//i sias reiksmes isirasysiu sienu ploti
if (i==0){
if(lab.checkUP(i, j)) t=5; //tikrina ar borderis, jei borderis, tai storesne siena, jei ne, tai plonesne
}
else {
if(lab.checkUP(i, j)) t=2;
}
if (i==lab.h-1){
if(lab.checkDOWN(i, j)) bot=5;
}
else{
if(lab.checkDOWN(i, j)) bot=2;
}
if(j==lab.v-1){
if(lab.checkRIGHT(i, j)) r=5;
}
else{
if(lab.checkRIGHT(i, j)) r=2;
}
if (j==0){
if(lab.checkLEFT(i, j)) l=5;
}
else{
if(lab.checkLEFT(i, j)) l=2;
}
label[i][j].setBorder(BorderFactory.createMatteBorder(t, l, bot,r , sienos));
label[i][j].setOpaque(true); //kad matytusi labelis
if(lab.isItWin(i, j)) label[i][j].setBackground(laimejimo);
else label[i][j].setBackground(laukeliai);
labirintas.add(label[i][j]);
}
}
}
public void online(){
try{
info = (connections) oos.readObject();
}catch(Exception e){
System.out.println(e.getCause());}
text.setText("Online:");
for (int i=0;i<info.names.length;i++){
text.setText(text.getText() + "\n" + info.names[i]);
label[info.x[i]][info.y[i]].setBackground(Color.gray);
if(lab.isItWin(info.x[i], info.y[i])) label[info.x[i]][info.y[i]].setBackground(laimejimo);
label[cooX][cooX].setBackground(Color.white);
}
}
}
public class connections {
public String[] names;
public int[] x;
public int[] y;
public void connections(){
names = new String[99];
x = new int[99];
y = new int[99];
for (int i=0;i<100;i++){
names[i]="";
x[i]=0;
y[i]=0;
}
}
public void info(int n,int x,int y,String name){
names[n]=name;
this.x[n]=x;
this.y[n]=y;
}
}
Here's what I get from stacktrace:
java.lang.NullPointerException
at client.connections.info(connections.java:24)
at server.Server$player.<init>(Server.java:90)
at server.Server.main(Server.java:57)
The class connections does not have a constructor so the variable names never gets initialized. So when you call the method info and it tries to set names[n]=name it throws a NullPointerException because names is still null.
It looks like you have a constructor because you have a method named connections which is the same as the class name. However, you gave the method a return type of void which prevents it from being a constructor as constructors do not have a return type.
Change that line to:
public class connections {
public connections(){
...
You will now get a NullPointerException because you are attempting to set the 100th location of your names array in your constructor of the connections class.
You create the names array with length 99.
Then your for loop iterates through the numbers 0 through 99 (less than 100).
The problem is that the highest allowable index of names is 98 which is the 99th location. So when you try to set names[99] = "" it throws a NullPointerException.
Change your for loop to only go up to 99 instead of 100:
public connections(){
names = new String[99];
x = new int[99];
y = new int[99];
for (int i=0;i<99;i++){
names[i]="";
x[i]=0;
y[i]=0;
}
}
Or change the arrays to be length 100 to match the for loop:
public connections(){
names = new String[100];
x = new int[100];
y = new int[100];
for (int i=0;i<100;i++){
names[i]="";
x[i]=0;
y[i]=0;
}
}
Java Class Names
In Java the convention is to name all classes with mixed case with the first letter capitalized. See Java Naming Convention
Methods should be name with mixed case with the first letter lowercase.
You should change your connections class as follows:
public class Connections {
public Connections(){
...