/* ************************************************************************** */
/*                                                                            */
/*                                                        :::      ::::::::   */
/*   ft_priority_queue.c                                :+:      :+:    :+:   */
/*                                                    +:+ +:+         +:+     */
/*   By: thrieg <thrieg@student.42mulhouse.fr>      +#+  +:+       +#+        */
/*                                                +#+#+#+#+#+   +#+           */
/*   Created: 2024/11/19 14:51:23 by thrieg            #+#    #+#             */
/*   Updated: 2025/02/16 19:07:06 by thrieg           ###   ########.fr       */
/*                                                                            */
/* ************************************************************************** */

#include "ft_priority_queue_private.h"

void	ft_insert_pq(t_priority_queue *pq, void *data, size_t priority)
{
	t_priority_queue_node	new_node;

	if (pq->size >= pq->capacity)
		ft_resize_pq(pq);
	new_node.data = data;
	new_node.priority = priority;
	pq->nodes[pq->size] = new_node;
	pq->size++;
	heapify_up(pq, pq->size - 1);
}

t_priority_queue	*create_priority_queue(
int capacity,
int (*compare)(void *, void *))
{
	t_priority_queue	*pq;

	pq = malloc(sizeof(t_priority_queue));
	if (!pq)
		return (NULL);
	pq->nodes = malloc(capacity * sizeof(t_priority_queue_node));
	if (!pq->nodes)
		return (free(pq), NULL);
	pq->size = 0;
	pq->capacity = capacity;
	pq->compare = compare;
	return (pq);
}

void	*peek(t_priority_queue *pq)
{
	if (pq->size == 0)
		return (NULL);
	return (pq->nodes[0].data);
}

void	*dequeue(t_priority_queue *pq)
{
	void	*ret;

	if (pq->size == 0)
		return (NULL);
	ret = pq->nodes[0].data;
	pq->nodes[0] = pq->nodes[pq->size - 1];
	pq->size--;
	heapify_down(pq, 0);
	ft_shrink_pq(pq);
	return (ret);
}

void	free_pq(t_priority_queue *pq)
{
	free(pq->nodes);
	free(pq);
}
