Search code examples
pythonpandasmatplotlibelementtreesubplot

How to resize the x-axis and make it different from the y-axis Matplotlib


I have the following development that I am working on with ElementTree, Pandas and Matplotlib modules in Python:

    def extract_name_value(signals_df):
        #print(signals_df)
        names_list = [name for name in signals_df['Name'].unique()]
        num_names_list = len(names_list)

        colors = ['b', 'g', 'r', 'c', 'm', 'y', 'k']

        # Creation Graphic
        fig = plt.figure(figsize=(18, 20))
        plt.suptitle(f'File PXML: {rootXML}', fontsize=20, fontweight='bold', color='SteelBlue', position=(0.75, 0.90))
        fig.tight_layout()
        i = 1
        for name in names_list:
            # get data
            data = signals_df[signals_df["Name"] == name]["Value"]
            datax = signals_df["Name"]
            # x = [n for n in range(len(data))]
            x = [n for n in range(len(datax))]
            print(x)
            # get color
            j = random.randint(0, len(colors) - 1)
            # add subplots
            ax = plt.subplot(num_names_list, 1, i)
            ax.plot(x, data, drawstyle='steps', marker='o', color=colors[j], linewidth=3)
            # plt.xticks(None)
            ax.set_ylabel(name, fontsize=12, fontweight='bold', color='SteelBlue', rotation=50, labelpad=45)
            ax.grid(alpha=0.4)
            i += 1

        plt.show()

I am getting the following error: Error Image

I have been looking for the error and I totally understand that the dimensions of x and y must be equal, but there is the possibility of making a graph where the x-axis is greater than the y-axis? and also the x-axis comes from a variable not related to the y-axis? how would this be?

The x-axis is the count of all the values it has in the Signal element of the xml file: I put it here because of how extensive it is and this value is larger than the y-axis, but how to contemplate the 3 values that I bring from the xml that are Singal Name, Signal Value as y-axis and Count of Signals as x-axis. I really appreciate your comments and help.


Solution

  • IIUC, you are trying to plot several stepped values agains their order of appearance (X-index) in XML file. Then you should plot against original dataframe's X values. I haven't changed your code much for style or such, just fixed a little.

    import xml.etree.ElementTree as ET
    import pandas as pd
    from matplotlib import pyplot as plt
    import random
    
    file_xml = 'example_un_child4.xml'
    
    def transfor_data_atri(rootXML):
        file_xml = ET.parse(rootXML)
        data_XML = [
            {"Name": signal.attrib["Name"],
             "Value": int(signal.attrib["Value"].split(' ')[0])
             } for signal in file_xml.findall(".//Signal")
        ]
        
        signals_df = pd.DataFrame(data_XML)
        extract_name_value(signals_df)
        
    def extract_name_value(signals_df):
        #print(signals_df)
        names_list = [name for name in signals_df['Name'].unique()]
        num_names_list = len(names_list)
    
        colors = ['b', 'g', 'r', 'c', 'm', 'y', 'k']
    
        # Creation Graphic
        #fig = plt.figure(figsize=(18, 20), sharex=True)
        fig, ax = plt.subplots(nrows=num_names_list, figsize=(10, 15), sharex=True)
        plt.suptitle(f'File PXML: {file_xml}', fontsize=20, fontweight='bold', color='SteelBlue', position=(0.75, 0.90))
        #fig.tight_layout()
        i = 1
        for pos, name in enumerate(names_list):
            # get data
            data = signals_df[signals_df["Name"] == name]["Value"]
            datax = signals_df["Name"]
            # x = [n for n in range(len(data))]
            #x = [n for n in range(len(datax))]
            #print(x)
            # get color
            j = random.randint(0, len(colors) - 1)
            # add subplots
            #ax[pos] = plt.subplot(num_names_list, 1, i)
            ax[pos].plot(data.index, data, drawstyle='steps', marker='o', color=colors[j], linewidth=3)
            # plt.xticks(None)
            ax[pos].set_ylabel(name, fontsize=12, fontweight='bold', color='SteelBlue', rotation=50, labelpad=45)
            ax[pos].grid(alpha=0.4)
            i += 1
        fig.tight_layout()
        plt.show()
    
    transfor_data_atri(file_xml)