Welcome, Guest. Please login or register. Did you miss your activation email?

Author Topic: Help with drawing NQueens problem using 2D arrays of objects  (Read 1415 times)

0 Members and 1 Guest are viewing this topic.

ToanBao122

  • Newbie
  • *
  • Posts: 8
    • View Profile
Help with drawing NQueens problem using 2D arrays of objects
« on: November 05, 2020, 02:14:40 am »
Hello everyone, I try to run a program to draw an empty chess board(each tile inside of the chess board is categorized as box) save for the queen piece at the position derived from the NQueens algorithm. My nqueens algorithm is correct, because I tested it, and It was able to give the correct position in the board(as in it was able to give me the correct rows, and columns of the queen). However, when I try to draw the whole thing, the window pop up in a white screen and close immediately without showing anything, while the terminal shows: "Process finished with exit code -1073741819 (0xC0000005)". Can you help me with this problem? Here's my code, and it is a bit lengthy as I manually implement a custom stack of queen using linked list( but I think you only needs to take a look at the nqueens, queen, box, board files, the others are irrelevant):
Board.h
#ifndef LINKEDLIST_TEMPLATE_BOARD_H
#define LINKEDLIST_TEMPLATE_BOARD_H


#include "Box.h"
#include "Queen.h"

class Board:public sf::Drawable, sf::Transformable {
private:
    Box** boxes;
    int n;
    int rows;
    int cols;


public:
    int getRow();
    int getCol();
    void addBox(Box& box);
    //Queen newQueen();
    //void printBoard();
    Board();
    Board(int size);
    Box**createArray(int new_rows, int new_cols);
    //void fillArray();
    //Box newBox();
    void draw(sf::RenderTarget &window, sf::RenderStates state) const;
    void addQueen(Queen queen);
};


#endif //LINKEDLIST_TEMPLATE_BOARD_H
Board.cpp
#include "Board.h"
void Board::addBox(Box &box) {
    for (int i = 0; i< rows; i ++)
    {
        for (int j = 0; j < cols; j++)
        {
            boxes[i][j] = box;
        }
    }
}
void printBoard(){}
Board::Board(){}
Board::Board(int size) {
    cols = 0;
    rows = 0;
    this->createArray(size,size);
}
Box** Board::createArray(int new_rows, int new_cols)
{
    rows = new_rows;
    cols = new_cols;
    boxes = new Box*[rows];
    for (int i = 0; i < rows; i++)
    {
        boxes[i] = new Box[cols];
    }
    return boxes;
}
/*void Board::fillArray() {
    for (int i = 0; i< rows; i ++)
    {
        for (int j = 0; j < cols; j++)
        {
            boxes[i][j] = newBox();
        }
    }
}*/

void Board::draw(sf::RenderTarget &window, sf::RenderStates states) const {
    for (int i = 0; i < rows; i++)
    {
        for (int j = 0; j < cols; j++)
        {
            window.draw(boxes[i][j],states);
        }
    }
}
void Board::addQueen(Queen queen) {
    boxes[queen.getRow()][queen.getCol()] = queen;
}
int Board::getRow() {
    return this->rows;
}
int Board::getCol() {
    return this->cols;
}
Box.h
#ifndef LINKEDLIST_TEMPLATE_BOX_H
#define LINKEDLIST_TEMPLATE_BOX_H


#include <SFML/Graphics.hpp>

class Box:public sf::Drawable, sf::Transformable {
protected:
    int col;
    int row;
    sf::Color color;
    sf::RectangleShape boxBackGround;
public:
   //sf::RectangleShape newBox(float x,float y);
    void draw(sf::RenderTarget &window, sf::RenderStates state) const;
    int getRow();
    int getCol();
    void setRow(int row);
    void setCol(int col);
    Box(int row, int col);
    void setBox();
    Box();
};
Box.cpp
#include "Box.h"
int Box::getCol() {
    return col;
}
int Box::getRow() {
    return row;
}
void Box::setCol(int col) {
    this->col = col;
}
void Box::setRow(int row) {
    this->row = row;
}
Box::Box(){
    this->setBox();
}
Box::Box(int row, int col) {
    this->row = row;
    this->col = col;
    this->setBox();

}
void Box::setBox() {
    boxBackGround.setSize({200.f,200.f});
    boxBackGround.setFillColor(sf::Color::White);
    boxBackGround.setPosition(210,210);
}
/*sf::RectangleShape Box::newBox(float x, float y)
{
    sf::RectangleShape s;
    s.setSize({200.f,200.f});
    s.setFillColor(sf::Color::White);
    s.setPosition(x,y);
    return s;
}*/

void Box::draw(sf::RenderTarget &window, sf::RenderStates state) const {
    window.draw(boxBackGround);
}
Queen.h
#ifndef LINKEDLIST_TEMPLATE_QUEEN_H
#define LINKEDLIST_TEMPLATE_QUEEN_H

#include "Box.h"

class Queen: public Box {
private:
    sf::Sprite queen;
    sf::Texture texture;
public:
    Queen();
    Queen(int row, int col);
    void draw(sf::RenderTarget &window, sf::RenderStates state) const;
    void setTexture();
    void setQueen();
};
Queen.cpp
#include "Queen.h"
Queen::Queen(){
    this->setTexture();
    this->setQueen();
}
Queen::Queen(int row, int col) {
    this->setCol(col);
    this->setRow(row);
    this->setTexture();
    this->setQueen();
}
void Queen::draw(sf::RenderTarget &window, sf::RenderStates state) const
{
    window.draw(this->queen);
}
void Queen::setTexture() {
    this->texture.loadFromFile("queen.png");
}
void Queen::setQueen() {
    this->queen.setTexture(this->texture);
    this->queen.setPosition(this->boxBackGround.getGlobalBounds().height-20,this->boxBackGround.getGlobalBounds().width-20);
}
NQueens.h
#ifndef LINKEDLIST_TEMPLATE_NQUEENS_H
#define LINKEDLIST_TEMPLATE_NQUEENS_H
#include"Stack.h"
#include"Queen.h"
#include "Board.h"
#include<cmath>
#include <SFML/Graphics.hpp>


class NQueens {
private:
    sf::RenderWindow*  window;
    bool isConflict();
    bool success;
    Stack<Queen> queens;
    Board board;
    Box theBox;
    int n;

public:
    NQueens(int n);
    NQueens();
    void run();
    void placeQueens();
    void initWindow();

};
NQueens.cpp
#include "NQueens.h"
#include <cmath>

NQueens::NQueens(int n): board(n),n(n){
    initWindow();
}
NQueens::NQueens(){}
void NQueens::run()
{
    placeQueens();
    board.addBox(theBox);
    int size = queens.size();
    for (int i =0;i<size;i++)
    {
        Queen temp = queens.pop();
        board.addQueen(temp);

    }
    while(this->window->isOpen())
    {
        sf::Event event;
        while(this->window->pollEvent(event)){
            if (event.type == sf::Event::Closed){
                this->window->close();
            }
        }
        this->window->clear(sf::Color::Black);
        this->window->draw(board);
        this->window->display();
    }
}
bool NQueens::isConflict() {
    if (queens.empty())
        return false;
    Queen top = queens.front();
    for (int i = 1; i <queens.size();i++)
    {
        if(queens.seek(i).getRow() == top.getRow())
            return true;
        if (queens.seek(i).getCol() == top.getCol())
            return true;
        if (abs(queens.seek(i).getCol()- top.getCol()) == abs(queens.seek(i).getRow() - top.getRow()))
            return true;
    }
    return false;
}
void NQueens::placeQueens()
{
    Queen q(1,1);
    success = false;
    queens.push(q);
    while (!success && !queens.empty())
    {

        if (isConflict())
        {
            while (!queens.empty() && queens.front().getCol() == n)
            {
                queens.pop();
            }
            if(!queens.empty())
            {
                Queen temp = queens.pop();
                temp.setCol(temp.getCol()+1);
                queens.push(temp);
            }
        }
        else if (queens.size() == n)
        {
            success = true;
        }
        else
        {
            Queen temp(queens.size()+1, 1);
            queens.push(temp);
        }
    }
}
void NQueens::initWindow() {
    this->window = new sf::RenderWindow(sf::VideoMode(1980,1080),"NQUEENS");
}
main.cpp
#include <iostream>
#include <SFML/Graphics.hpp>
#include "NQueens.h"
int main() {
    NQueens nq(5);
    nq.run();
}
Any help is much appreciated! Thank you and sorry for the lengthy post.

Stauricus

  • Sr. Member
  • ****
  • Posts: 369
    • View Profile
    • A Mafia Graphic Novel
    • Email
Re: Help with drawing NQueens problem using 2D arrays of objects
« Reply #1 on: November 05, 2020, 11:37:26 am »
have you tried debugging it? so you can at least know in which line the problem starts?
Visit my game site (and hopefully help funding it? )
Website | IndieDB

ToanBao122

  • Newbie
  • *
  • Posts: 8
    • View Profile
Re: Help with drawing NQueens problem using 2D arrays of objects
« Reply #2 on: November 05, 2020, 10:05:46 pm »
The problem seems to in the following: Board::addQueen in Board.cpp; and when declare the Box at: "class Box:public sf::Drawable, sf::Transformable", I think.
« Last Edit: November 05, 2020, 10:09:13 pm by ToanBao122 »

Stauricus

  • Sr. Member
  • ****
  • Posts: 369
    • View Profile
    • A Mafia Graphic Novel
    • Email
Re: Help with drawing NQueens problem using 2D arrays of objects
« Reply #3 on: November 06, 2020, 03:43:20 pm »
probably unrelated to SFML, but actually to C++ itself.
check trough the debugger the values of "queen.getRow()", "queen.getCol()", and the size of "boxes" inside the adQueen function.
Visit my game site (and hopefully help funding it? )
Website | IndieDB

eXpl0it3r

  • SFML Team
  • Hero Member
  • *****
  • Posts: 10819
    • View Profile
    • development blog
    • Email
Re: Help with drawing NQueens problem using 2D arrays of objects
« Reply #4 on: November 10, 2020, 10:52:16 am »
An access violation mostly occurs when trying to access objects that no longer exist or that go beyond the given vector/array.
Step through you code in a debugger and keep track of your boxes array.
Also I highly recommend to use a 1D std::vector and map the the x and y position onto an index with i=x+(y*width) and x=i*((i / width)*height) and y=i/width.
Official FAQ: https://www.sfml-dev.org/faq.php
Official Discord Server: https://discord.gg/nr4X7Fh
——————————————————————
Dev Blog: https://duerrenberger.dev/blog/

 

anything