How to normalize images not between 0 and 1

zehranrgi: <p>Hi, in the below code, I normalized the images with a formula. And, I saved images in this format. However, I want to know can I do it with <code>torch.nn.functional.</code> <code>normalize</code> … I don’t want to change images that are in the folder, because I want to visualize predicted images and I can’t see the original images with this way.</p>
<pre><code class="lang-auto">import numpy as np
from PIL import Image

files = src

def normalize(files):
    k= 0 

    for i in files:
        image = Image.open(i)
        new_image = image.resize((600, 600))
        pixels = np.asarray(image)

        pixels = pixels.astype('float32')
        mean, std = pixels.mean(), pixels.std()
        # global standardization of pixels
        pixels = (pixels - mean) / std  
        print(pixels)


        outfile_name = i.replace(".png", ".npy")  

        with open(outfile_name, 'wb') as f:
            np.save(f, pixels)
            np.save(f, np.array([mean, std]))  
        print(k)

        with open(outfile_name, 'rb') as f:
            norm_t = np.load(f)  # Load normalized array
            mean_std = np.load(f)  # Load mean and std 
            mean, std = tuple(mean_std) 
            k =k+1

            t = norm_t*std + mean  # Unnormalized (get the original pixels before normalizing)
            t = np.round(t.clip(0, 255)).astype(np.uint8)  # Convert from float to uint8
            img = Image.fromarray(t, 'RGB')
            img.save("degis{0}.png".format(k))
            
            
            img.show()
  
normalize(files)
</code></pre>

suraj.pt: <p>Are you looking for <a href="https://pytorch.org/vision/stable/generated/torchvision.transforms.Normalize.html#torchvision.transforms.Normalize" class="inline-onebox">Normalize — Torchvision 0.12 documentation</a>? This doesn’t change your input images as it transforms the image tensor in memory.</p>
<p>Eg:</p>
<pre><code class="lang-auto">img_tensor = torchvision.io.read_image(img_path) 
mean, std = img_tensor.mean(), img_tensor.std()

normalize = torchvision.transforms.normalize(mean, std)
norm_tensor = normalize(img_tensor)
unnorm_tensor = norm_tensor * std + mean

torchvision.io.write_png(unnorm_tensor, 'degis0.png')</code></pre>

zehranrgi: <p>I didn’t understand one thing from the documentation. If I used it like that:  <code>transforms.Compose([transforms.Normalize()])</code>, and yes it will not change my images, however, I have to give mean and std. And, how I can give your example code logic here? As I got from your code, I have to save new png images as like before.</p>
<p>I hope I explained my question as clearly. Thanks for your help.</p>

suraj.pt: <p>You can use it without Compose… Normalize() is like any other module that you can call on an input.</p>
<p>Yes, you will need to give mean and std. In many examples, you’ll see a 3-dimensional mean and std tensor for a 3-channel image. This ensures that the normalization happens channel-wise.</p>
<p>You can save it if you like, I included that line because in your <code>normalize()</code> you are doing that. Here are some ways to visualize without needing to save the tensor to an image: <a href="https://pytorch.org/vision/stable/auto_examples/plot_visualization_utils.html#sphx-glr-auto-examples-plot-visualization-utils-py">https://pytorch.org/vision/stable/auto_examples/plot_visualization_utils.html#sphx-glr-auto-examples-plot-visualization-utils-py</a></p>
<blockquote>
<p>And, how I can give your example code logic here?</p>
</blockquote>
<p>Sorry, I’m not sure what you mean - can you clarify this?</p>

zehranrgi: <ol>
<li>
<p>I mean that if I want to use this code, how I can give these normalized images to the model?</p>
</li>
<li></li>
</ol>
<blockquote>
<p>Yes, you will need to give mean and std. In many examples, you’ll see a 3-dimensional mean and std tensor for a 3-channel image</p>
</blockquote>
<p>I understood better now.<br>
So if use this formula, find these 3-dim values and give them to the module, will it be the same/right way to implement the algorithm that I shared?</p>
<pre><code class="lang-auto">mean = 0.0
meansq = 0.0
count = 0

for index, data in enumerate(train_loader):
    mean = data.sum()
    meansq = meansq + (data**2).sum()
    count += np.prod(data.shape)

total_mean = mean/count
total_var = (meansq/count) - (total_mean**2)
total_std = torch.sqrt(total_var)
print("mean: " + str(total_mean))
print("std: " + str(total_std))

cited from (https://discuss.pytorch.org/t/computing-the-mean-and-std-of-dataset/34949/20)
</code></pre>

zehranrgi: <p>What I want to do overall:</p>
<p>I should actually find the mean and standard deviation for the channel of the image I am interested in. Then, calculate the new value (p-m)/s of the pixel in that channel and use it as input.</p>
<p>But, I couldn’t find a proper way to use it without saving images after applying this algorithm.</p>
<p>Does my problem make sense? <a class="mention" href="/u/suraj.pt">@suraj.pt</a></p>

suraj.pt: <p>You don’t need to save the image to disk. You can directly use the returned tensor in your function.</p>
<pre><code class="lang-auto"># load img from disk
img_tensor = torchvision.io.read_image(img_path) 
mean, std = img_tensor.mean(), img_tensor.std()

# normalize
normalize = torchvision.transforms.normalize(mean, std)
normalized_img_tensor = normalize(img_tensor)

# use normalized image as inputs to your func
my_fn(inputs=normalized_img_tensor)
</code></pre>