Skip to content

Repository files navigation

Graph-Based Feed-Forward Neural Network Library in C

Work In Progress

This project is still a work in progress, many things will be subject to change in the near future.

Overview

This repository hosts a library for constructing, training, evaluating, and managing feed-forward neural network models, all implemented in C. This project leverages graph theory and adjacency matrices to represent the network's structure, providing a more "theoretical" perspective on neural network design.

The project allows for minimal dependency compilation, as well as data types defined at compile time. See below for details.

Key Features

  • Model Construction: Define neural networks as graphs using nodes and weighted edges, represented through adjacency matrices.
  • Training Module: Implement training routines to adjust weights and optimize network performance.
  • Inference Engine: Compute outputs from the network trough a given prompt.
  • Memory Management: Create and delete models to maintain optimal resource usage.
  • Demonstrative Example: Train the network to compute the square root of an integer (provided in binary form), showcasing a practical application of the library.

Educational Focus

The primary goal of this project is to deepen understanding of feed-forward neural networks by building one from the ground up. Detailed design decisions, implementation insights, and theoretical underpinnings are documented in Documentation.odt.

Testing

The tests I've done during the development are integrated within the Tests folder, where edge cases and incorrect inputs are validated, ensuring the reliability of the library.


Building the project

This project uses a Makefile. Ensure you have GNU Make and GCC installed on your system. Follow the steps below:

  1. Clone the Repository

    git clone <repository_url>
    cd <repository_directory>
  2. Compile the Project

    Use the make command to compile the source files and generate the executable:

    make

    This will produce the executable named main.a.out.

  3. Additional Makefile Commands

    • Clean Build Artifacts

      To remove the compiled object files and the executable, use:

      make clean
  4. Adding New Source or Header Files

    If you add new .c or .h files to the project, you must update the Makefile accordingly. This involves:

    • Updating Source Files

      Add the new .c files to the SRC variables. For example, if you add new_module.c, include it as follows:

      SRC_NEW_MODULE = new_module.c
    • Updating Object Files

      Similarly, add the corresponding .o files to the OBJ variables:

      OBJ_NEW_MODULE = new_module.o
    • Linking New Object Files

      Ensure that the new object files are included in the linking step for the target executable:

      $(TARGET): $(OBJ_MATRIX) $(OBJ_MODEL) $(OBJ_MAIN) $(OBJ_NODE) $(OBJ_NEW_MODULE)
      	$(CC) $(CFLAGS) -o $(TARGET) $(OBJ_MATRIX) $(OBJ_MODEL) $(OBJ_MAIN) $(OBJ_NODE) $(OBJ_NEW_MODULE) -lm
    • Compiling New Source Files

      Add rules to compile the new source files:

      new_module.o: $(SRC_NEW_MODULE) $(HEADERS)
      	$(CC) $(CFLAGS) -c $(SRC_NEW_MODULE)

    After updating the Makefile, run make again to build the project with the new files.


Enabling / Disabling Debug verbosity ; Changing the data types ; Disabling the need for dependencies

The project uses the header file settings.h to manage settings and the enabling or disabling of features.

The majority of things are handled at compile time using Defines, so that the excluded features won't inlfuence the performance negatively and will make the executable lighter. Also enhancing the overall understandability of the code.

  • Minimal Dependency compilation: The only truly needed external functions are malloc and calloc. Set DEBUG to 0 to disable all debug messages and prevent inclusion of <stdio.h>; tweak the data types so that there is no need to include any other library and then you are good to go!. (compile dependency free!)

  • Flexible data types: Customize the data types the program uses at compile time directly in settings.h to match your platform or precision needs.

    • parameter type (ffw_param_t),
    • structure counters (ucount_t/count_t),
    • and loop indices (uindex_t/index_t)

Here is a list of the modifiable settings:

bool enum

This enum allows for a fast and reliable definition of the bool type, across all files.

The use of this enum is used instead of the inclusion of the stdbool library to allow for standard library free compilation.

Can be useful mostly for code readability purposes.

DEBUG

If set to 1, then all the debug messages will be printed.

Also enabling the definition of an "ad hoc" DEBUG_PRINT function.

Note: since debug messages need to be printed, the standard library stdlib will be included, if you would like to not include any libraries, you should not use this function

MORE

If set to 1, certain portion of the code will be added.

These aren't necessary for the normal operation of the code, nor they should be considered as a mean to "making the program more able" or more "complete".

This macro is intended to add other "in code" tools for courious developers that would like to modify the code.


File Structure

This section provides an overview of the key files in this library and explains their roles. You can use this guide to navigate and understand how each file contributes to the project.

main.c

  • Purpose:
    Serves as the primary entry point for the library. (as it contains the only main() function of the library)

  • Details:

    • It includes all header and source files in the library.
    • Mainly used for test and demonstration purposes, it also contains some sample test functions to demonstrate the library's functionality.
    • You may uncomment the provided test routines to see immediate output and behavior just for reference or curiosity (^_^)
  • Usage:
    Developers can use main.c as a starting point to experiment with the library. In a production environment, you might replace or exclude this file to integrate the library into your own projects.

settings.h (Under contruction: this section will be surely updated in the future)

  • Purpose:
    Provides a centralized location for global settings, compiler macros, type definitions, and other configurable parameters used throughout the project.

  • Key Features:

    • Debug Configuration:
      • DEBUG macro controls whether debug logging is enabled.
      • DEBUG_PRINT macro prints file and line information when debug mode is active.
    • Additional Flags:
      • VERBOSE toggles more detailed debugging messages.
      • autoMode switches between automatic and manual training modes.
      • MORE includes or excludes optional code paths deemed non-essential but potentially useful.
    • Unified Typedefs:
      • Bool enum provides a simple, project-wide boolean convention (TRUE = 1, FALSE = 0).
  • Usage:

    • Include settings.h in any file that needs these macros, flags, or type definitions.
    • Adjust the macro values in settings.h to customize debugging verbosity, enable or disable features, and unify project-wide data types.
    • Expect ongoing additions or modifications to this file as the project evolves.

License

This project is licensed under the Creative Commons Attribution-NonCommercial 4.0 International (CC BY-NC 4.0). This permits sharing and adapting the code for non-commercial purposes, provided appropriate credit is given to the original author. For more information, refer to the LICENSE file.

About

My first attempt at graph teory with a super simple neural network

Resources

Stars

0 stars

Watchers

1 watching

Forks

Releases

Packages

Used by

Contributors

Languages